Determine names of Menu Bar shortcuts for use in scripts

Skip to the bottom for the TL/DR version.

Howdy folks. While getting a lot of help with one of my last questions I realized what would really be handy is a way to determine the names of the shortcuts in the Menu Bar so as to write scripts that interact with them.

(My original question had to do with polling the battery levels of my mouse and keyboard and save those results to a variable so Keyboard Maestro could alert me when they fall below a certain threshold.)

After several days of searching both this website and Google (and being distracted by yet another project) I have not come up with anything.

Basically, I would like to know if there’s a way to find out the names of my Menu Bar shortcuts so I can have AS “click” on them to do various things. The current one I am curious about is Keyboard Maestro as I wrote a macro that clicks on the shortcut and then on “cancel specific macro” so I can see what macros are currently running and cancel a specific one. But it’s based off of Keyboard Maestro’s “found image” action which is pretty reliable but not 100%. So I would like to figure out the “name” of Keyboard Maestro’s shortcut in the Menu Bar so AS can click directly on it.

But I would REALLY like to know how to find out those names for ALL of my shortcuts so I can use them in a variety of scripts in the future without having to bug yall so much haha.

I did find this script which allows me to put in what I THINK is the name but obviously it’s still like shooting in the dark.

tell application "System Events" to get every process whose name contains "keyboard maestro"

[TL/DR] Does anybody know how to determine the names of Menu Bar shortcuts so AS can interact with them?

Ok after more Google Fu I came up with this script:

tell application "System Events" to tell process "Keyboard Maestro Engine" to ¬
	ignoring application responses
		click menu bar item 1 of menu bar 2
	end ignoring

do shell script "killall System\\ Events"

tell application "System Events" to ¬
	ignoring application responses
		click menu item "Cancel" of menu 1 of menu bar item 1 of menu bar 2 of application process "Keyboard Maestro Engine" of application "System Events"
	end ignoring

The ignoring and killall is because there was a long delay between the two clicks. I don’t know why but apparently it’s common as I found that solution on another website.

Is this the best way to accomplish this or is there a better/faster/more elegant way of accomplishing this?

Bump…anybody have any ideas on this? The script I posted has actually stopped working for some reason :-/ :frowning:

Hi,

not quite sure what you’re asking, i found this script, maybe it could be of any help?

kind regards,
EricLipton

If you need the “name” of a specific menu item, easiest and fastest way that comes to my mind is opening Automator, starting “Record” (red round button), clicking the menu item, and stopping “recording”.

Next copy all resulting lines from Automator’s window, open Script-Editor and “paste”.
Apart from a lot of waitings and other stuff it somewhere lists the menu item clicked-on.

menu bar item 1 of menu bar 2 of application process "Keyboard Maestro Engine"

The menu bar icons can be split into two groups: those belonging to the system; and those belonging to user-installed applications.

The former belong to the process called “SystemUIServer”, and you can enumerate them with this command (wrapped inside a suitable tell block targetting System Events):

every menu bar item of menu bar 1 of process "SystemUIServer"

The latter group of icons that belong to user-installed applications are children of the corresponding application process’s menu bar 2 (menu bar 1 being the parent of the application’s main menu items when the application has focus). Therefore, generally speaking, if an application named Foobar has an icon in the menu bar, it can be accessed via:

menu bar item 1 of menu bar 2 of application process "Foobar"

To enumerate all of the processes of user-installed applications that have menu bar icons:

name of every process whose class of menu bar 2 = menu bar

AppleScript: 2.7
Operating System: macOS 10.13

When I run :

tell application "System Events"
	name of every process whose class of menu bar 2 = menu bar
end tell

I get :
→ {“popCalendar”, “FastScripts”}
Two custom items are missing : MalwareBytes and SMARTReporter

Yvan KOENIG running High Sierra 10.13.6 in French (VALLAURIS, France) samedi 15 décembre 2018 12:11:57

That’s where “generally speaking” becomes applicable, as there’ll always be some applications who register their UI elements differently.

I downloaded MalwareBytes just to examine it. It’s menu bar icon is referenced like so:

menu bar item 1 of menu bar 1 of application process "FrontendAgent"

So, awkwardly, it belongs to menu bar 1 of a process called “FrontendAgent”.

If you want a “catch-all” solution that, I believe, grabs all the menu bar icons belonging to both the system and the user, then:

every menu bar item of every menu bar of every application process whose subrole = "AXMenuExtra"

It returns a nested hierarchy, but it can still be iterated by way of item 1 of… etc. as if it were a one-dimensional list.

Thanks.

I’m too lazy to build a code automating the entire process.
Here is the best result I was able to get.

tell application "System Events"
	--	(every menu bar item of every menu bar of every application process whose subrole = "AXMenuExtra")
	
	(*
{{}, {}, {{}}, {}, {}, {{}}, {}, {}, {{}}, {}, {{menu bar item "Centre de notifications" of menu bar 1 of application process "SystemUIServer" of application "System Events", menu bar item "Siri" of menu bar 1 of application process "SystemUIServer" of application "System Events", menu bar item 3 of menu bar 1 of application process "SystemUIServer" of application "System Events", menu bar item 4 of menu bar 1 of application process "SystemUIServer" of application "System Events", menu bar item 5 of menu bar 1 of application process "SystemUIServer" of application "System Events", menu bar item 6 of menu bar 1 of application process "SystemUIServer" of application "System Events", menu bar item 7 of menu bar 1 of application process "SystemUIServer" of application "System Events", menu bar item 8 of menu bar 1 of application process "SystemUIServer" of application "System Events", menu bar item 9 of menu bar 1 of application process "SystemUIServer" of application "System Events"}}, {}, {{}}, {{menu bar item "Spotlight" of menu bar 1 of application process "Spotlight" of application "System Events"}}, {{}}, {}, {}, {}, {{}, {menu bar item 1 of menu bar 2 of application process "popCalendar" of application "System Events"}}, {{menu bar item 1 of menu bar 1 of application process "SMARTReporter" of application "System Events"}}, {{}, {menu bar item 1 of menu bar 2 of application process "FastScripts" of application "System Events"}}, {}, {}, {}, {}, {{menu bar item 1 of menu bar 1 of application process "FrontendAgent" of application "System Events"}}, {{}}, {{}}, {{}}, {{}}, {}, {}, {}, {}, {}, {{}}, {}, {{}}, {}, {}, {{}}, {}, {{}}, {}, {}, {}, {}, {{}}, {{}}, {{}}}
*)
	set theItems to {}
	set end of theItems to name of menu bar item "Centre de notifications" of menu bar 1 of application process "SystemUIServer" of application "System Events"
	set end of theItems to name of menu bar item "Siri" of menu bar 1 of application process "SystemUIServer" of application "System Events"
	set end of theItems to description of menu bar item 3 of menu bar 1 of application process "SystemUIServer" of application "System Events"
	set end of theItems to description of menu bar item 4 of menu bar 1 of application process "SystemUIServer" of application "System Events"
	set end of theItems to description of menu bar item 5 of menu bar 1 of application process "SystemUIServer" of application "System Events"
	set end of theItems to description of menu bar item 6 of menu bar 1 of application process "SystemUIServer" of application "System Events"
	set end of theItems to description of menu bar item 7 of menu bar 1 of application process "SystemUIServer" of application "System Events"
	set end of theItems to description of menu bar item 8 of menu bar 1 of application process "SystemUIServer" of application "System Events"
	set end of theItems to description of menu bar item 9 of menu bar 1 of application process "SystemUIServer" of application "System Events"
	try
		name of application process of (menu bar item 1 of menu bar 2 of application process "popCalendar" of application "System Events")
	on error errMsg
		set end of theItems to my extractName(errMsg)
	end try
	
	
	try
		name of application process of (menu bar item 1 of menu bar 1 of application process "SMARTReporter" of application "System Events")
	on error errMsg
		set end of theItems to my extractName(errMsg)
	end try
	
	try
		name of application process of (menu bar item 1 of menu bar 2 of application process "FastScripts" of application "System Events")
	on error errMsg
		set end of theItems to my extractName(errMsg)
	end try
	try
		name of application process of (menu bar item 1 of menu bar 1 of application process "FrontendAgent" of application "System Events")
		
	on error errMsg
		set theName to my extractName(errMsg)
		--if theName contains "FrontendAgent" then set end of theItems to "MalwareBytes"
		if theName is "\"FrontendAgent\"." then set end of theItems to "MalwareBytes"
	end try
	
end tell
theItems
(*
{"Centre de notifications", "Siri", "AppleScript", "time machine", "bluetooth", "text input", "volume 19 %", "Horloge", "Wi-Fi, Wi-Fi non activé.", "\"popCalendar\".", "\"SMARTReporter\".", "\"FastScripts\".", "MalwareBytes"}
*)

on extractName(errMsg)
	set AppleScript's text item delimiters to "application process "
	set theName to last text item of errMsg
	set AppleScript's text item delimiters to ""
	return theName
end extractName

Yvan KOENIG running High Sierra 10.13.6 in French (VALLAURIS, France) samedi 15 décembre 2018 20:11:17

This will do something similar:

tell application "System Events" to get the name of every process whose subrole of menu bar item 1 of menu bars contains "AXMenuExtra"

It returns only :

{“SystemUIServer”, “Spotlight”, “popCalendar”, “SMARTReporter”, “FastScripts”, “FrontendAgent”}

Yvan KOENIG running High Sierra 10.13.6 in French (VALLAURIS, France) samedi 15 décembre 2018 21:07:31

Yes, that’s correct. I noted yours itemised the SystemUIServer, substituting in a description of the UI element that represents the menu bar icon in place of the name of the process that owns it. That’s fine, it’s why I was careful to say that they were similar, not the same. Just utilise whatever best suits your needs.