(Apple's inability to determine) Desktop size

One of the Safari scripts that Apple offers, tiles two frontmost browser windows over the screen (http://a772.g.akamai.net/7/772/51/75f01daeedb09a/www.apple.com/applescript/safari/scripts/tandem.sit)
The more exciting part of it is how Apple determines the desktop size (as even the modest system parameters still are inaccessible).
Too bad there is a scripting error here.
In my case (“tell process Finder”) gives a type 10 error:


tell application "System Events"
		tell process "Finder"
			repeat with i from 1 to number of windows
				if the position of window i is {0, 0} then
					return the size of window i
				end if
			end repeat
		end tell

Now my question is:
You can get around the error by substituting “application” for “process”, but that doesn’t yield anything useful in my case.
What would Apple want here (if the number of windows and their position can be anything !) and what could be the aim of getting the size of a window whose position is (0,0) i.e. desktop ?

Getting the screen resolution.
This has been discussed recently at AUL, and were thrown other two methods. Here:

{word 3 of (do shell script "defaults read /Library/Preferences/com.apple.windowserver | grep -w Width") as number, ¬
	word 3 of (do shell script "defaults read /Library/Preferences/com.apple.windowserver | grep -w Height") as number}

Slower.
And:

set prefs to read alias ((path to startup disk as text) & "Library:Preferences:com.apple.windowserver.plist")
set off1 to (offset of "<key>Width</key>
				<integer>" in prefs) + 30
set off2 to (offset of "</integer>
			</dict>
		</array>
	</array>
</dict>
</plist>
" in prefs) - 1
set width to text from character off1 of prefs to character off2 of prefs as number
set off1 to (offset of "<key>Height</key>
				<integer>" in prefs) + 31
set off2 to (offset of "</integer>
				<key>IODisplayLocation" in prefs) - 1
set height to text from character off1 of prefs to character off2 of prefs as number
{width, height}

Note that some characters where truncated here… (substitute ASCII 13 -CR- for ASCII 10 -LF- in strings)

The script works on my machine without errors and returns the desktop size as {1024, 768}

I did have to add one more…

end tell

to the script

tell application "System Events"
	tell process "Finder"
		repeat with i from 1 to number of windows
			if the position of window i is {0, 0} then
				return the size of window i
			end if
		end repeat
	end tell
end tell

If you consider that the desktop is nothing more than a folder that covers entire screen and has no window decorations, then the apple code makes sense.

There isn’t any Finder command that I can call from within the block:

tell application "System Events"
tell PROCESS "Finder"
[all regular Finder commands give errors here]
end tell
end tell

I can make calls to APPLICATION “Finder” though, but that doesn’t make sense from within a System Events call. Also, it doesn’t return any window with position (0,0)
It may be that I do not have the latest scriptable System Events.app (I have a standard Jaguar 10.2.3, no Developer Tools), but even then, when a folder has no window decorations, how could it’s window have a position anyway…?
To me, this coode doesn’t makes sense…

When you say “tell process finder”, you’re not going to execute any finder command. Theorically, you’re targeting the Finder to be the target of “System Events”’ commands & classes.
Perhaps you are confussed because of the existence of a double “tell” statement. Bur you are “telling” to “process” Finder, not to the Finder itself… And “process” is a property of “System Events”. Eg:

tell application "TextEdit" --> or "System Events"
     tell window 1 --> or "process finder" = tell [object] [identifier]
          --> do whatever
     end tell
end tell

You could also write:

tell application "System Events"
     tell (first process whose name is "Finder")
          --> do whatever
     end tell
end tell

Or:

tell application "System Events" to tell item 1 of (processes) to --> do whatever

That’s because you can’t use Finder specific commands: you’re not telling application finder, but class “process” identifier “finder” of application “System Events”… The only tell app block is “System Events”, and you can only use its commands.

Latest version of “System Events” displays “1.2” as its version, and it’s located at “/System/Library/CoreServices/”. You can d/l it at http://www.apple.com/applescript/GUI/

Anyway, the folder is in fact a folder… Besides it can be absurd, it’s useful! :rolleyes:

JJ,

Thanks for your extensive explanation.
Although I never install beta’s, this made me curious enough and… indeed it works.
Plus - whatever absurd it may be - there IS a lot more interesting stuff in the new System Events dictionary…

Sure! :smiley:
New GUI scripting capabilities are amazing!

Okay, I’ve installed System Events 1.2, I’ve got Enable access for assistive devices enabled, and I’ve got the desktop size script (from Apple) copied correctly in Script Editor but when I run it I get an NSCannotCreateScriptCommandError and Script Editor highlights the {0, 0} in the script. Anyone know what’s going on?

I know this is an old post, but none of this works any more with Lion. I tried every script in this thread, all gave different results, some gave errors, but none of these gave me the screen resolution.

So here’s how you do it in OSX 10.7 (Lion):

tell application "Finder" to return bounds of window of desktop

Easy as pie…

EDIT
Note: I also remember this works fine for Snow Leopard… and also probably back a few more versions of OSX.

Aesthir

Except it can’t handle multiple screens.

Ahhh… thanks! I didn’t even think of that as it doesn’t apply to me :smiley:

Aesthir

If you want that info badly enough, this code will do:


tell application "System Information"
	activate
	set detail level of front document to "min"
	set rawdata to profile of front document   -- this is slow, perhaps 10 seconds
end tell

set oldTID to AppleScript's text item delimiters
set AppleScript's text item delimiters to {"Graphics/Displays:", "Hardware:"}

set tlst to every text item of rawdata
set graphicsinfo to item 2 of tlst     -- this will still require some parsing to get the value(s) as numbers

set AppleScript's text item delimiters to oldTID

return graphicsinfo

Thanks, but I was really pointing out that the offered code din’t cope with it.

Personally, I generally use AppleScriptObjC:

on mainScreenSize()
	return (current application's NSScreen's mainScreen()'s visibleFrame()'s |size|()) as list
end mainScreenSize

on primaryScreenSize()
	return (current application's NSScreen's screens()'s objectAtIndex_(0)'s visibleFrame()'s |size|()) as list
end primaryScreenSize

But obviously that can’t be used everywhere.

Or there’s:

set f to (path to preferences from local domain as Unicode text) & "com.apple.windowserver.plist"
tell application "System Events" to set {|DisplaySets|:{displays}} to value of property list file f

repeat with thisDisplay in displays
	set {|Width|:w, |Height|:h} to thisDisplay
	set thisDisplay's contents to {w, h}
end repeat

displays --> {{1440, 900}}

If you know there’s only one monitor:

set f to (path to preferences from local domain as Unicode text) & "com.apple.windowserver.plist"
tell application "System Events" to set {|DisplaySets|:{{{|Width|:w, |Height|:h}}}} to value of property list file f

{w, h} -- > {1440, 900}

These work back to at least Mac OS 10.4, although the numbers returned on that system are reals.

Sure, that’s a far more elegant approach. I just wanted to point out a way it can be done, if awkwardly, in straight Applescript.

All this stuff with “com.apple.windowserver.plist” doesn’t work for me… which is why I posted my one-liner. This is the entire contents of my plist file:

Which obviously doesn’t tell me much about resolution. It seems to be a popular answer in this thread but simply doesn’t work for all cases.

Aesthir

Well. That seems a bit bare. But unless and until I get Lion I can’t comment further.

However, it reminds me that for some months after I got my MacBook Pro (with Snow Leopard), this method was returning entirely the wrong dimensions in a script I use. It turned out that the “com.apple.windowserver.plist” file had been migrated across from my G5 and the data it contained were for the G5’s cinema display ” although this wasn’t affecting the behaviour of the MacBook Pro’s display. Zapping the file and restarting to let the MacBook generate a new one cured the problem with the script.

On my machine, the value of the ‘Quartz2DExtremeEnabled’ property (in the record returned by ‘value of property list file f’ in my script) is a boolean.

(Somewhat off-topic, I notice that one of the other properties is labelled ‘CGSInterocitorSelectMode’. An interocitor was an alien-designed device in a 1950s sci-fi film called “This Island Earth”. A Web search reveals a third-party audio application with that name for the iPhone, but I can’t imagine “com.apple.windowserver.plist” having a setting for it. Intriguing…)

I’m still on SL too but I’ve never used one of these methods. If you have a single screen maybe this method works in Lion

set rawResolutions to do shell script "system_profiler SPDisplaysDataType | grep -i resolution"
set screenResolutions to {word 2 of rawResolutions as integer, word 4 of rawResolutions as integer}

It does work.
With this modification also for multiple displays

set rawResolutions to do shell script "system_profiler SPDisplaysDataType | grep -i resolution"
set resolutionList to {}
repeat with aParagraph in (get paragraphs of rawResolutions)
	set end of resolutionList to {word 2 of aParagraph as integer, word 4 of aParagraph as integer}
end repeat
resolutionList