• Open Menu Close Menu
  • Apple
  • Shopping Bag
  • Apple
  • Mac
  • iPad
  • iPhone
  • Watch
  • TV
  • Music
  • Support
  • Search apple.com
  • Shopping Bag

Lists

Open Menu Close Menu
  • Terms and Conditions
  • Lists hosted on this site
  • Email the Postmaster
  • Tips for posting to public mailing lists
Re: accessing a property of an object in AppleScript
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: accessing a property of an object in AppleScript


  • Subject: Re: accessing a property of an object in AppleScript
  • From: has <email@hidden>
  • Date: Sat, 8 Nov 2008 23:26:56 +0000

Mark Sanvitale wrote:

This should be a super basic question.  Alas, I have spent many hours  
banging my head against this problem.
[...]
{position:{0, 280}, maximum value:missing value, name:"Print
", size:
{259, 19}, subrole:missing value, class:menu item, minimum  
value:missing value, enabled:false, selected:false,  
role:"AXMenuItem", help:missing value, title:"Print
", value:missing  
value, entire contents:{}, description:"menu item", focused:missing  
value, orientation:missing value}

I want to access the enabled property.  I eventually discover that I  
can access a property like so:

return name of (get properties of printMenuItem)

which correctly returns "Print
".  Now, I replace name with enabled  
and I get an error.  A few properties work in the above statement  
(e.g. class, size) but most do not, including my precious enabled  
property.

Welcome to the obfuscated mess that is AppleScript's context-sensitive grammar. Your problem is a result of all the cunning compiler trickery that AppleScript uses to create that nice, English-like syntax (where white space is both a keyword delimiter and a legal character within keywords), and Apple's chronic inability/failure to adequately explain its behaviour and limitations to users.

Basically, 'tell application "NAME" ... end' blocks serve two purposes: 1. to identify a default target for runtime commands, and 2. to make the parser recognise keywords defined in the specified application's terminology resource in addition to the keywords defined in the AppleScript language's terminology resource. 

Outside of that 'tell application' block, only AppleScript's built-in terminology is available to the parser. So any time you write an application-defined keyword in a script it must appear within a 'tell' block (or 'using terms from' block) that identifies the application at compile-time, or else it won't compile correctly (the only exceptions being keywords that are also defined by AppleScript, e.g. 'name', 'class'). e.g. This compiles as intended:

tell application "System Events"
    set props to properties of menu item "Print…" of menu "File" of ¬
        menu bar item "File" of menu bar 1 of process "Safari"
    return enabled of props
end tell

but this doesn't:

tell application "System Events"
set props to properties of menu item "Print…" of menu "File" of ¬
menu bar item "File" of menu bar 1 of process "Safari"
end tell
return enabled of props

Look real closely in Script Editor, and (assuming you haven't changed the default colours) you'll notice AppleScript's pretty printer uses different colours to indicate application-defined keywords versus user-defined identifiers. 'enabled' needs to be an application-defined keyword, not an identifier, same as the application-defined 'enabled' property in the record returned by System Events.

...

FWIW, other Apple event bridges are largely immune to these sorts of problems as they use existing language structures to construct Apple event queries, commands and symbols, e.g. Ruby appscript does all its terminology translation at runtime: queries and commands are constructed using Ruby methods, and type/enumerator/property name symbols are represented by instances of Ruby's Symbol class.

require "appscript"; include Appscript
require 'pp'

se = app("System Events")
app("Safari").activate
print_menu_ref = se.processes["Safari"].menu_bars[1].menu_bar_items["File"].menus["File"].menu_items["Print\342\200\246"]

pp print_menu_ref.enabled.get
# result:
  true

record = print_menu_ref.properties_.get
pp record
# result:
  {:class_=>:menu_item,
   :role=>"AXMenuItem",
   :minimum_value=>:missing_value,
   :focused=>:missing_value,
   :subrole=>:missing_value,
   :position=>[0, 280],
   :value=>:missing_value,
   :name=>"Print\342\200\246",
   :maximum_value=>:missing_value,
   :description=>"menu item",
   :entire_contents=>[],
   :selected=>false,
   :enabled=>true,
   :orientation=>:missing_value,
   :help_=>:missing_value,
   :size=>[259, 19],
   :title=>"Print\342\200\246"}

pp record[:enabled]
# result:
  true


HTH

has

p.s. If you're comfortable with other languages, it's worth noting that OS X's Carbon/Cocoa accessibility APIs can be accessed directly from C/ObjC; you don't have to go through System Events if you don't want to. (Though programmatically controlling other applications via their GUIs is still fundamentally evil, of course.)
-- 
Control AppleScriptable applications from Python, Ruby and ObjC:
http://appscript.sourceforge.net

 _______________________________________________
Do not post admin requests to the list. They will be ignored.
AppleScript-Users mailing list      (email@hidden)
Help/Unsubscribe/Update your Subscription:
Archives: http://lists.apple.com/archives/applescript-users

This email sent to email@hidden

  • Prev by Date: RE: extending an command
  • Next by Date: RE: extending an command
  • Previous by thread: Re: accessing a property of an object in AppleScript
  • Next by thread: RE: accessing a property of an object in AppleScript
  • Index(es):
    • Date
    • Thread