How to Hide All Windows of an App Other Than the Front One

I would like to know if the following is possible:

For some apps (such as Mail), there might be Messege Viewer window open, as well as a window for the current email being written as well as other windows for the Mail app.

Is there a command so that all the other windows for the Mail app (or what other app as the case may be) are minimised other than the one that is at the forefront?

The Manipulate a Window Action does not seem to offer the right combination of options to do this.

2 Likes

Execute an AppleScript in an AppleScript action:

This is the script text:

tell application "Mail"
	activate
	repeat (count (windows)) - 1 times
		set miniaturized of window 2 to true
	end repeat
end tell

Note: We have to repeatedly minimize window 2 because when the first window 2 is minimized apparently the window that formerly was window 3 becomes window 2 and so on.

In one fell swoop:

tell application "Mail"
  tell (windows whose id is not (get id of front window) and visible is true)
    set miniaturized to true
  end tell
end tell

-Chris

1 Like

This is ā€¦ perfect :smile:

How do you write it for any process who is frontmost?

Chris and Tom,

Thank you very much for the actions.

Victor

This is very hard, at least for me. I have spent many hours on this, but have learned a lot.

Here is a general purpose script that should work well with all apps.
I have tested it with:
ā€¢ Finder
ā€¢ Apple Mail
ā€¢ Outlook 2011
ā€¢ Evernote
ā€¢ Chrome
ā€¢ Safari

It is NOT perfect. There could be issues with Finder if you have actual Finder windows with the same name.

If you have any ideas on how to improve, or find issues, please post.

Minimize All App Windows Except Frontmost

(*
===============================================================================
  Minimize All App Windows Except Frontmost
===============================================================================

VER:   1.0    LAST UPDATE:   2016-04-09

PURPOSE:
  ā€¢ ============================================================================
  Minimize All App Windows Except Frontmost

AUTHOR:    JMichaelTX
          Find any bugs/issues or have suggestions for improvement?
          Contact me via PM or at blog.jmichaeltx.com/contact/

REQUIRED:
  1.  Mac OS X Yosemite 10.10.5+
  2.  Mac Applications -- NONE are required, but this has been tested with:
        ā€¢ Finder
        ā€¢ Apple Mail
        ā€¢ Outlook 2011
        ā€¢ Evernote
        ā€¢ Chrome
        ā€¢ Safari
        
  3.  INTERNAL FUNCTIONS:
      ā€¢ removeDups(pList)

REF:  The following were used in some way in the writing of this script.
  1.  
===============================================================================
   
*)
use AppleScript version "2.4" -- Yosemite (10.10) or later
use scripting additions

tell application "System Events"
  
  --- GET FRONTMOST APP ---
  --    CAUTION:
  --      1. Some commands do NOT work when using tell application with 
  --        a variable instead of explicit text
  --      2. Different Apps have different commands to minimize a window
  --      3. Thus, I had to use System Events with a UI keyboard command
  --    If you know of a better way, please let me know
  
  set frontAppName to item 1 of (get name of processes whose frontmost is true)
  
  tell process frontAppName
    
    set numWin to count of windows
    
    --- GET LIST OF WINDOW NAMES ---
    --    CAUTION:
    --      1. Some apps, like the Finder, can have different windows with the same name
    --      2. Some apps, like the Finder, report duplicate windows in error
    
    set winTitleList to title of every window
    set winTitleList to my removeDups(winTitleList) -- needed for Finder windows
    
    --- Remove 1st Window (the current Frontmost) from List ---
    set winTitleList to (items 2 thru -1 of winTitleList)
    
    repeat with windowTitle in winTitleList
      -- Select/Activate Each Window to Make Frontmost --
      click menu item windowTitle of menu 1 of menu bar item "Window" of menu bar 1
      delay 0.1
      
      -- Minimize the Window --
      keystroke "m" using command down -- this is same as CMD-M
    end repeat
    
  end tell
end tell


--~~~~~~~~~~~~~~~~~~~~~~~ END OF MAIN SCRIPT ~~~~~~~~~~~~~~~~~~~~

on removeDups(pList)
  local newList
  set newList to {}
  repeat with iItem from 1 to count pList
    set itemStr to item iItem of pList
    if itemStr is not in newList then set end of newList to itemStr
  end repeat
  return newList
end removeDups

Hey Tom,

There's no perfect way to make that generic, but JM has the general idea.

-Chris

Okay, I've fiddled with this quite a bit:

------------------------------------------------------------
# Auth: Christopher Stone
# dCre: 2016/04/10 06:00
# dMod: 2016/04/13 06:37
# Appl: System Events
# Task: Minimize all Windows Except the Front One in the Front App.
# Tags: @Applescript, @Script, @System_Events, @Minimize, @Windows
------------------------------------------------------------

tell application "System Events"
  tell (first process whose frontmost is true)
    set winList to windows whose subrole is "AXStandardWindow"
    
    if length of winList > 1 then
      set winList to rest of winList
      
      repeat with theWindow in winList
        try
          tell theWindow to set value of attribute "AXMinimized" to true
        end try
      end repeat
      
    end if
    
  end tell
end tell
------------------------------------------------------------

So far it's worked with every app I've tried it on.

-Chris

Edited 2016/04/13 06:38 CST to fix the flaw Alain noticed below.

2 Likes

I already expected something along the lines when I saw your other script :wink:

Seems to work nicely. Except in Firefox the frontmost window gets minimized.

Hey Tom,

Hmm... Not on my system. (OSX 10.11.4)

Firefox 45.0.1

Tested with Script Debugger, FastScripts, and Keyboard Maestro.

Not sure what might be happening at your end.

-Chris

Iā€™m investigating. Sometimes it works in FF, sometimes the front window gets minimized. It seems that it depends if Iā€™ve done something in the front window (e.g. adding a tab).

Can you reproduce: Close all FF windows and close FF. Start FF. Type 3 Ɨ āŒ˜N. Launch the macro. -> The window that stays on screen is the oldest one.

Hey Tom,

That only seems to happen here when none of the windows have any content.

What about at your end?

-Chris

No, they do have content (they start with the default URL (ā€œHomepageā€)). The frontmost window only gets ā€œrecognizedā€ as frontmost after Iā€™ve changed the URL or opened another tab.

Same FF and OS version here.

But I donā€™t think itā€™s worth investigating much in FF abnormalitiesā€¦

Thanks Christopher (and @JMichaelTX) for this script.

I've just fiddled a very little bit to avoid minimizing a solitary window:

tell application "System Events"
  tell (first process whose frontmost is true)
    set winList to windows whose subrole is "AXStandardWindow"
    
    if length of winList > 1 then
      set winList to rest of winList
      repeat with theWindow in winList
        try
          tell theWindow to set value of attribute "AXMinimized" to true
        end try
      end repeat
    end if
    
  end tell
end tell

--Alain

2 Likes

Nice script, Chris.
Thanks.

Alain, great catch and fix. :+1:
Thanks for sharing.

I've tested your script and it seems to work.

Interestingly, collapsed windows apparently have subrole AXUnknown or AXDialog (for some reason), so this doesnā€™t work for unminimizing all of an applicationā€™s windows. See also Minimize all windows of an application.

Eh?

Oh, that's what mine looked like before I ā€œoptimizedā€ it.

Good catch.

-Chris

I had an engineering boss once, who often said:

'Better' is the enemy of 'good enough'

:wink:

I didn't always agree with that, since it depends on just how good "good enough" is.