An AppleScript to stack windows in Xcode

Nov 13, '07 07:30:00AM

Contributed by: farcrafter

Xcode, or any Apple app for that matter, has a poor implementation of window stacking and default window placement. So I wrote an AppleScript that will stack Xcode windows. It would be fairly easy to adopt it to another application, but each target will have a different way of getting the list of windows to stack. For example, this script stacks only windows with names matching source documents.

This script is geared towards a single monitor, but will handle the monitor changing resolution. I have a laptop, but I often plug in an external monitor, and this will dynamically adapt. If you have multiple monitors, you could hard code the usable area you want the windows to stack in. If you know a way to get the dimensions of just the main device in AppleScript, post it.

This script stacks in a number of columns, not just one. It gives priority to a minimum window width, and figures out from there how many columns to make. The actual window width is the calculated from the number of columns, but that could be skipped if you prefer a fixed window width.

Here's the script:

tell application "Finder"
  -- get the bounds of the Desktop window
  set {desktopLeft, desktopTop, desktopRight, desktopBottom} to bounds of container window of desktop
  set screenWide to desktopRight - desktopLeft
  set screenTall to desktopBottom - desktopTop
end tell

tell application "Xcode"
  set screenTall to (screenTall - 24) -- leave room for menu bar
  set screenWide to (screenWide - 120) -- leave room on right
  
  set windowsPerStack to 6
  set minimumWide to 720 -- minimum width of window
  set maximumColumn to ((screenWide / minimumWide) - 0.4) as integer -- number of colums to stack in
  set maximumRow to windowsPerStack - 1
  set borderTall to 16 -- space under bottom of stack
  set borderWide to 8 -- space between stacks
  set marginTall to 20 -- space between windows in stack
  set marginWide to 10 -- space between windows in stack
  
  set windowWide to ((screenWide / maximumColumn) as integer) - borderWide - marginWide * maximumRow
  set windowLeft to (windowWide * 0) + borderWide
  
  set theExtra to 0
  set theCount to 0
  set theNames to name of every source document
  set theWindows to {}
  
  -- locate every window that will be stacked
  repeat with theWindow in windows
    if ((visible of theWindow) and (0 is level of theWindow)) then
      set theTitle to title of theWindow
      if (theTitle is in theNames) then
        set theWindows to theWindows & {theWindow}
      end if
    end if
  end repeat
  
  -- stack all the windows
  set theFinal to 0
  set theTotal to count of theWindows
  repeat with theIndex from 1 to theTotal
    set theWindow to item theIndex of theWindows
    
    if (theCount is 0) then
      if ((theTotal - theIndex) < maximumRow) then
        set theFinal to maximumRow - (theTotal - theIndex)
      end if
    end if
    
    -- reverse flips and flops to change stack direction
    set theFlips to theCount + theFinal
    set theFlops to maximumRow - (theCount + theFinal)
    set windowLeft to borderWide + marginWide * theFlops + (windowWide + maximumRow * marginWide + borderWide) * theExtra
    set windowTall to screenTall - marginTall * maximumRow
    set bounds of theWindow to {windowLeft, borderTall + marginTall * theFlips, windowLeft + windowWide, windowTall + marginTall * theFlips}
    
    set theCount to theCount + 1
    if (theCount > maximumRow) then
      set theCount to 0
      set theExtra to theExtra + 1
      if (theExtra ≥ maximumColumn) then
        set theExtra to 0
      end if
    end if
  end repeat
end tell
In Xcode 3, it is easy to tie a script to a command key using Edit User Scripts. In earlier versions, it took a little more trickery, but I am guessing there is already a tip for that. I would prefer that a variant of this script run whenever a new window is opened, and automatically stack that one window, but I have not figured that out yet.

[robg adds: I haven't tested this one.]

Comments (2)


Mac OS X Hints
http://hints.macworld.com/article.php?story=20071030182948434