Hello!
Joys script used 3, then 4 seconds, with the count dialog decoupled, mine did indeed use 5, then 5, Marks didn’t run for some reason. 20 duplicate windows, 19 were closed, with a total of 59 windows open when the scripts were run.
I’ll just say that I do things with the targets of the finder windows, in order to have something to unique to work from that works in every situation. And that the script should be fairly robust, and work from whatever app.
Working with the targets of windows, and coercing finder references into aliases, must necessarily be a bit more expensive, than dealing with just text, but that is the only way you can assure that you have unique windows when you have, as the windows won’t be unique when using “normal” window titles, and two subfolders are carrying the same name.
It considers Finder windows only, so I don’t deal with clippings windows, not knowing if it is possible to open duplicates of those anyway. But it do consider computer windows, and spotlight windows in current space.
Here it is, working so far, maybe I’ll try to optimize the loop further, and see if I can shave off more here. I doubt I can shave off more in the loops, but I’ll give it a try!
Edit
I am pondering adding the old part of my script as curtsey to those using posix paths in their window title, in the mean time, while I am pondering this, I have added a dialog, like a progress dialog, to show that something is indeed happening, leveraging on “ignoring application responses”, to show users (me), that something are progressing.
Edit+
Added three comments.
script pruneDupFWins
-- © McUsr 2012 28.10.2012 completely rewritten to cope with all cases of window titles, and computer windows
property parent : AppleScript
property scriptTitle : "Close Duplicate Windows"
property FinderIcon : a reference to file ((path to library folder from system domain as text) & "CoreServices:Finder.app:Contents:Resources:Finder.icns")
# COLLECTING NECESSARY DATA
# fastest way to make SystemEvents, get the window count for the windows appearing in the current space.
local fwc, clcount, prevApp # Finder Window Count, close count
set clount to 0
try
tell application id "sevs"
set prevApp to (name of every process whose frontmost is true and visible is true) as text
tell application process "Finder" to set fwc to count its windows
end tell
if fwc = 0 then return 0
on error
return 0 # Finder wasn't running!
end try
if fwc > 10 then
ignoring application responses
tell application id "com.apple.systemuiserver"
activate
try #
display dialog "Finding Duplicate Finder Windows in current space..." with title my scriptTitle buttons {"Ok"} default button 1 with icon my FinderIcon giving up after (fwc div 10)
end try
end tell
end ignoring
end if
# script for enhancing speed, not needed really
script o
property ides : {} # ides of wins
property targs : {} # targets
property tmpTargs : {} # third pair of tmp lists !
property tmpIdes : {}
end script
local startTargs, startIdes # firs pair of tmp lists for collecting
# collecting targets and ids of Finders windows, as fast as possible.
tell application id "MACS"
set {startTargs, startIdes} to {target, id} of its every Finder window
end tell
# PREPROCESSING OF FINDER-DATA BEFORE WE CAN LOOK FOR DUPLICATES
# we have to convert the Targets into text, The spotlight windows, just disappears in the process
# as we get a runtime error, «class ccmp» is a way to say computer-object outside a finder tell block.
local curtag, siftedTargs, siftedIdes # second pair of tmplists for sifting and preparing
set {o's targs, o's ides, siftedTargs, siftedIdes} to {startTargs, startIdes, {}, {}}
repeat with i from 1 to length of startTargs
try
set curTarg to item i of o's targs # curtag used for minimizing references
set end of siftedTargs to curTarg as alias -- as text
set end of siftedIdes to item i of o's ides
on error
try
if class of curTarg = «class ccmp» then
set end of siftedTargs to "Computer"
set end of siftedIdes to item i of o's ides
end if
end try
end try
end repeat
set {startTargs, startIdes} to {missing value, missing value}
# Finding the last finder window in our space, we have grabbed THEM all. Finder windows in other spaces
# has a higher index, than our last window number as obtained from system events.
local fwcAdj # Finder window count . Adjusted
set {o's ides, fwcAdj} to {siftedIdes, length of siftedIdes}
tell application id "MACS"
repeat
tell its Finder window id (item fwcAdj of o's ides) to if index of it > fwc then
set fwcAdj to fwcAdj - 1
else
exit repeat
end if
end repeat
end tell
set fwc to fwcAdj
# This count are the fwc first windows in our list we must consider for pruning duplicates of here.
# SIFTING OUT ANY DUPLICATE FINDER WINDOWS
set {o's ides, o's targs} to {items 1 thru fwc of siftedIdes, items 1 thru fwc of siftedTargs}
local tids, searchlist, idx, idList # used for having a searchlist, and the index for found elements
# idlist is the list of ids of finder windows we are going to close
set {tids, idList} to {AppleScript's text item delimiters, {}}
# What happens here, is that we take each line of the list of finder windows, chops it off the list
# and looks for duplicates, which corresponding id's are put onto the idlist for closure.
# we just churn thru the whole list until all duplicates are removed as fast as possible.
# if anybody has an idea of a faster way, I am all ears!
repeat
# this construct will fail when there are only one item left on the list.
try
set {searchItm, o's targs, o's ides} to {item 1 of o's targs, items 2 thru -1 of o's targs, items 2 thru -1 of o's ides}
set searchlist to o's targs
# an inlined handler indexofItem by Emmanuel Levy
set AppleScript's text item delimiters to return
set searchlist to return & searchlist & return
set AppleScript's text item delimiters to ""
try
set idx to -1 + (count (paragraphs of (text 1 thru (offset of (return & searchItm & return) in searchlist) of searchlist)))
on error
set idx to 0
end try
repeat while idx > 0
set end of idList to item idx of o's ides
if idx = 1 then
set {o's targs, o's ides} to {rest of o's targs, rest of o's ides}
else if idx = length of o's targs then
set {o's targs, o's ides} to {items 1 thru -2 of o's targs, items 1 thru -2 of o's ides}
else
set {o's targs, o's ides} to {items 1 thru (idx - 1) of o's targs & items (idx + 1) thru -1 of o's targs, items 1 thru (idx - 1) of o's ides & items (idx + 1) thru -1 of o's ides}
end if
set searchlist to o's targs
# an inlined handler indexofItem by Emmanuel Levy
set AppleScript's text item delimiters to return
set searchlist to return & searchlist & return
set AppleScript's text item delimiters to ""
try
set idx to -1 + (count (paragraphs of (text 1 thru (offset of (return & searchItm & return) in searchlist) of searchlist)))
on error
set idx to 0
end try
end repeat
on error
exit repeat
end try
end repeat
set AppleScript's text item delimiters to tids
# CLOSING ANY DUPLICATE FINDER WINDOWS
set clcount to length of idList
if clcount ≠0 then
tell application id "MACS"
repeat with wid in idList
tell its Finder window id wid to close
end repeat
end tell
if clcount = 1 then
set msgText to "I closed 1 window!"
else
set msgText to "I closed " & clcount & " windows!"
end if
else
set msgText to "Nothing to do!"
end if
tell application id "MACS"
activate
try # comment out the line below when testing for speed
display dialog msgText with title my scriptTitle buttons {"Ok"} default button 1 with icon my FinderIcon giving up after 1.2
end try
end tell
tell application prevApp to activate
end script
# set t1 to (current date)
tell pruneDupFWins to run
(*
set t2 to (current date) - t1
tell application "Finder"
activate
display dialog "message " & t2
end tell
*)