http://www.autohotke...opic.php?t=3699
It searches for, lists, and deletes upon approval, all empty folders within a user-specified location. Folders do not go to the Recycle Bin.
; DeleteEmptyFolders Utility 1.3.1 ; by Decarlo !#e:: ; comment this line when using it for command line ; added support for commandline parameters and an auto-delete mode with logfile. ; with command line parameters, selectionEF corresponds to the first, and targetFolderEF to the second. ; note: sending function parameters thru a hotkey achieves a similar mode. ; streamlined the output code. ; added handling of Folders which contain only Empty Subfolders.*** ; progress window: enabled dragging, added option to remove window (for faster run) ; detects if target folder doesnt exist, and handles if it is itself empty ; fixed initialization. if 2 <> ; command-line parameters received DeleteEmptyFolders() else { selectionEF = ;1e ; input values here to bypass the Input prompt. targetFolderEF = C:\ ; leave at least 1 param blank to show the Input prompt. DeleteEmptyFolders() } return DeleteEmptyFolders() ; use of local function vars avoids possible naming conflicts with common variables of other routines { SetFormat, Float, 0.3 global 0, 1, 2 ; recognize command-line parameters global selectionEF, targetFolderEF emptytargetFolderEF= backSlashCheck= Splash= possibleEmptySubFoldersFolders= countFoldersEmptySubFolders=0 emptySubfoldersFolderList= countTopmostEmptyFolders=0 topmostEmptyFoldersList= countFilesFolders= countFolders= countEmptyFolders= emptyFolderList= FileFolderList= FolderList= if 2 <> { selectionEF = %1% targetFolderEF = %2% } else if ( selectionEF AND targetFolderEF ) ; function parameters received (from this same script) 1 := 1 ; this construct avoids the next Else (Input prompt) if the necessary values exist. else { InputBox, selectionEF, DeleteEmptyFolders Utility, Please select:`n1. list/delete empty folders`n2. list/delete empty folders and list all folders`n3. list/delete empty folders and list all folders and files`nInclude A (capital) to auto-delete empty folders (caution). no progress window.`nInclude w to run without progress window (better speed).`nInclude e to also find folders containing only empty subfolders.`nThese parameters also apply to command-line mode.,, 700, 240,,,,, 1e If (ErrorLevel<>0 OR selectionEF="") EXIT DEF_1 = Enter the complete path of the target folder.`nAll its empty folders will be listed and a prompt shown for approval to delete.`nFor long paths`, it is better to copy-paste from the AddressBar. ifInString, selectionEF, 1 InputBox, targetFolderEF, DeleteEmptyFolders Utility, %DEF_1%,, 700, 170,,,,, C:\ else ifInString, selectionEF, 2 InputBox, targetFolderEF, DeleteEmptyFolders Utility, %DEF_1%`nAll subfolders of the target folder will also be listed.`n,, 700, 170,,,,, C:\ else ifInString, selectionEF, 3 InputBox, targetFolderEF, DeleteEmptyFolders Utility, %DEF_1%`nAll files and folders of the target folder will also be listed.`n,, 700, 170,,,,, C:\ If (ErrorLevel<>0 OR targetFolderEF="") EXIT } StringCaseSense, on ifInString, selectionEF, A { StringReplace, selectionEF, selectionEF, A, autoW StringCaseSense, off } if selectionEF not contains 1,2,3 ; verify parameters { ifInString, selectionEF, auto { GoSub CreateLogName FileAppend, selectionEF parameter did not contain 1, 2, or 3. Exiting., %logName% } else msgbox,,, invalid parameter, .7 EXIT } ifNotInString, targetFolderEF, C:\ { ifInString, selectionEF, auto { GoSub CreateLogName FileAppend, %targetFolderEF% is an invalid targetFolderEF parameter. Exiting., %logName% } else msgbox,,, invalid parameter, .7 EXIT } ifInString, selectionEF, 1 { StringReplace, selectionEF, selectionEF, 2 StringReplace, selectionEF, selectionEF, 3 } else ifInString, selectionEF, 2 StringReplace, selectionEF, selectionEF, 3 ifNotInString, selectionEF, w Splash=1 ; only built-in cmds can be used on same line above StringRight, backSlashCheck, targetFolderEF, 1 if backSlashCheck=\ StringTrimRight, targetFolderEF, targetFolderEF, 1 targetFolderEFLocation:=targetFolderEF . "\" targetFolderEF:=targetFolderEF . "\*" sleep 100 ; because splash doesnt appear sometimes startTimeEmptyFolders=%A_TickCount% IfExist, %targetFolderEFLocation% Loop, %targetFolderEF%, 1, 1 { if A_index=1 { emptytargetFolderEF=N if Splash=1 { SplashTextOn, 500, 100, DeleteEmptyFolders Utility, Text WinSet, AlwaysOnTop, off, DeleteEmptyFolders WinSet, Enable,, DeleteEmptyFolders } ifInString, selectionEF, 3 GoSub DEF_SearchAll else GoSub DEF_SearchFolders ifInString, selectionEF, e GoSub DEF_FindEmptySubfoldersFolders BREAK } } else { ifInString, selectionEF, auto { GoSub CreateLogName FileAppend, %targetFolderEFLocation% does not exist. Exiting., %logName% } else msgbox, %targetFolderEFLocation%`n`ndoes not exist. EXIT } endTimeEmptyFolders=%A_TickCount% timeTaken:=(endTimeEmptyFolders-startTimeEmptyFolders)/1000. SplashTextOff ifInString, selectionEF, auto GoSub DEF_Results_NoUserPrompt else GoSub DEF_Results RETURN ; return from the function DEF_FindEmptySubfoldersFolders: ;msgbox,,, searching only-empty-subfolders folders, .7 Loop, Parse, emptyFolderList, `n, `r ; use previous results: generate checklist { tracePathEmptyFolder = %A_LoopField% Loop { if A_LoopField = BREAK StringLen, DEF_Length_1, tracePathEmptyFolder StringGetPos, DEF_Loc1, tracePathEmptyFolder, \, R if DEF_Loc1 = 2 ; path cannot be shorter than C:\ BREAK StringTrimRight, tracePathEmptyFolder, tracePathEmptyFolder, % DEF_Length_1 - DEF_Loc1 ifInString, tracePathEmptyFolder, %targetFolderEFLocation% ; item must be in target folder { ifNotInString, possibleEmptySubFoldersFolders, %tracePathEmptyFolder%`r`n { possibleEmptySubFoldersFolders = %possibleEmptySubFoldersFolders%%tracePathEmptyFolder%`r`n ControlSetText, Static1, %tracePathEmptyFolder%, DeleteEmptyFolders Utility } } else BREAK } } Sort, possibleEmptySubFoldersFolders, U Loop, parse, possibleEmptySubFoldersFolders, `n, `r ; find all folders containing only empty subfolders { flagEmptyFolder = ; reset for each loop field num=%A_Index% Loop, %A_LoopField%\*, 0, 1 ; check files only, not folders { ControlSetText, Static1, %A_LoopFileFullPath%, DeleteEmptyFolders Utility if A_Index = 1 { flagEmptyFolder = N BREAK } } if flagEmptyFolder= { emptySubfoldersFolderList=%emptySubfoldersFolderList%%A_LoopField%`r`n countFoldersEmptySubFolders+=1 } } ; narrow the list: find topmost folders containing only empty subfolders (they contain all the items) Loop, Parse, emptySubfoldersFolderList, `n, `r ; use previous results { if A_LoopField = BREAK tracePathEmptyFolder = %A_LoopField% ControlSetText, Static1, %tracePathEmptyFolder%, DeleteEmptyFolders Utility StringLen, DEF_Length_1, tracePathEmptyFolder StringGetPos, DEF_Loc1, tracePathEmptyFolder, \, R StringTrimRight, tracePathEmptyFolder, tracePathEmptyFolder, % DEF_Length_1 - DEF_Loc1 ControlSetText, Static1, %tracePathEmptyFolder%, DeleteEmptyFolders Utility ifNotInString, emptySubfoldersFolderList, %tracePathEmptyFolder%`r`n { topmostEmptyFoldersList = %topmostEmptyFoldersList%%A_LoopField%`r`n countTopmostEmptyFolders+=1 } } Sort, emptySubfoldersFolderList Sort, topmostEmptyFoldersList, U return DEF_SearchAll: Loop, %targetFolderEF%, 1, 1 { FileFolderList=%FileFolderList%%A_LoopFileFullPath%`r`n countFilesFolders+=1 countFolders+=1 flagEmptyFolder= FileGetAttrib, Attribs, %A_LoopFileFullPath% ifInString, Attribs, D { Loop, %A_LoopFileFullPath%\*, 1 { ControlSetText, Static1, %A_LoopFileFullPath%, DeleteEmptyFolders Utility if A_index=1 { flagEmptyFolder=N BREAK } } if flagEmptyFolder= { emptyFolderList=%emptyFolderList%%A_LoopFileFullPath%`r`n countEmptyFolders+=1 } } else countFolders-=1 } return DEF_SearchFolders: Loop, %targetFolderEF%, 2, 1 { ifInString, selectionEF, 2 FolderList=%FolderList%%A_LoopFileFullPath%`r`n countFolders+=1 flagEmptyFolder= Loop, %A_LoopFileFullPath%\*, 1 { ControlSetText, Static1, %A_LoopFileFullPath%, DeleteEmptyFolders Utility if A_index=1 { flagEmptyFolder=N BREAK } } if flagEmptyFolder= { emptyFolderList=%emptyFolderList%%A_LoopFileFullPath%`r`n countEmptyFolders+=1 } ; integrating the empty-subfolder search into this routine takes longer (almost 2x). } Sort, emptySubfoldersFolderList return DEF_EditorMsgStrings: ifInString, selectionEF, e ; e = option to also find folders containing empty subfolders { DEF_EmpSub1 = %countFoldersEmptySubFolders% folders containing only empty subfolders also found.`r`n`r`n%countTopmostEmptyFolders% topmost folders containing only empty subfolders.`r`n`r`n DEF_EmpSub2 = %countFoldersEmptySubFolders% Folders containing only empty subfolders:`r`n`r`n%emptySubfoldersFolderList%`r`n`r`n`r`n%countTopmostEmptyFolders% Topmost folders containing only empty subfolders:`r`n`r`n%topmostEmptyFoldersList%`r`n`r`n } else { DEF_EmpSub1 = DEF_EmpSub2 = } DEF_1 = %DEF_TimeString%`r`n`r`n%countEmptyFolders% empty folders of %countFolders% total found inside %targetFolderEFLocation%`r`n`r`n%DEF_EmpSub1%time: %timeTaken% sec`r`n`r`n`r`n%countEmptyFolders% Folders without items:`r`n`r`n%emptyFolderList%`r`n`r`n`r`n%DEF_EmpSub2%---------------------------------`r`n`r`n DEF_2 = The following folders could not be deleted:`r`n`r`n ifInString, selectionEF, 1 DEF_msg=%DEF_1%%DEF_2% else ifInString, selectionEF, 2 DEF_msg=%DEF_1%List of all %countFolders% subfolders:`r`n`r`n%FolderList%`r`n`r`n---------------------------------`r`n`r`n%DEF_2% else DEF_msg=%DEF_TimeString%`r`n`r`n%countEmptyFolders% empty folders of %countFilesFolders% total files/folders found inside %targetFolderEFLocation%`r`n`r`n%DEF_EmpSub1%total folders: %countFolders%`r`n`r`ntime: %timeTaken% sec`r`n`r`n`r`n%countEmptyFolders% Folders without items:`r`n`r`n%emptyFolderList%`r`n`r`n`r`n%DEF_EmpSub2%---------------------------------`r`n`r`nList of all %countFilesFolders% files/folders:`r`n`r`n%FileFolderList%`r`n`r`n---------------------------------`r`n`r`n%DEF_2% return CreateLogName: Time := A_Now StringTrimRight, Time, Time, 2 StringRight, HourMin, Time, 4 StringTrimRight, Time, Time, 4 Time := Time . "." . HourMin logName := "logfile_DeleteEmptyFolders_" . Time ".txt" return DEF_Results_NoUserPrompt: Sort emptyFolderList Sort FolderList Sort FileFolderList GoSub CreateLogName if countEmptyFolders= { if emptytargetFolderEF= { FileRemoveDir %targetFolderEFLocation% FileAppend, %DEF_TimeString%`r`n`r`n%targetFolderEFLocation% is an empty folder. Deleted., %logName% } else ifInString, selectionEF, 1 FileAppend, %DEF_TimeString%`r`n`r`nNo empty folders were found in %targetFolderEFLocation%., %logName% else { DEF_1 = %DEF_TimeString%`r`n`r`n0 empty folders of DEF_2 = found inside %targetFolderEFLocation%`r`n`r`n DEF_3 = time: %timeTaken% sec`r`n`r`n%emptyFolderList%`r`n`r`n---------------------------------`r`n`r`nList of all%A_Space% ifInString, selectionEF, 2 DEF_msg=%DEF_1%%countFolders% total %DEF_2%%DEF_3%%countFolders% subfolders:`r`n`r`n%FolderList%`r`n else DEF_msg=%DEF_1%%countFilesFolders% total files/folders %DEF_2%total folders: %countFolders%`r`n`r`n%DEF_3%%countFilesFolders% files/folders:`r`n`r`n%FileFolderList%`r`n FileAppend, %DEF_msg%, %logName% } } else { GoSub DEF_EditorMsgStrings FileAppend, %DEF_msg%, %logName% listToDelete = %emptyFolderList% GoSub DeleteEmpty_NoUserPrompt if countFoldersEmptySubFolders { DEF_1 = 1 listToDelete = %topmostEmptyFoldersList% GoSub DeleteEmpty_NoUserPrompt } } return DeleteEmpty_NoUserPrompt: errorList= errorsOccurred= Loop, Parse, listToDelete, `n, `r { if A_LoopField= BREAK FileRemoveDir, %A_LoopField%, 1 ; recurse to remove empty subfolders if ErrorLevel=1 { errorList=%errorList%%A_LoopField%`r`n errorsOccurred=1 } } if errorsOccurred=1 FileAppend, %errorList%, %logName% else { if DEF_1 = 1 FileAppend, of folders containing only empty subfolders:`n<none>`n`n, %logName% else FileAppend, of folders without items:`n<none>`n`n, %logName% } return ; end of auto-delete section ;------------------------------------------- DEF_Results: Sort emptyFolderList Sort FolderList Sort FileFolderList if countEmptyFolders= { if emptytargetFolderEF= { msgbox, 4097, DeleteEmptyFolders Utility, %targetFolderEFLocation%`n`nis an empty folder.`n`nDelete it? ifMsgBox, OK FileRemoveDir %targetFolderEFLocation% } else ifInString, selectionEF, 1 msgbox, No empty folders were found inside`n`n%targetFolderEFLocation% else { Run, notepad,,, Npid WinActivate, ahk_pid %Npid% WinWaitActive, ahk_pid %Npid% FormatTime, DEF_TimeString DEF_1 = %DEF_TimeString%`r`n`r`n0 empty folders of DEF_2 = found inside %targetFolderEFLocation%`r`n`r`n DEF_3 = time: %timeTaken% sec`r`n`r`n%emptyFolderList%`r`n`r`n---------------------------------`r`n`r`nList of all%A_Space% ifInString, selectionEF, 2 DEF_msg=%DEF_1%%countFolders% total %DEF_2%%DEF_3%%countFolders% subfolders:`r`n`r`n%FolderList%`r`n else DEF_msg=%DEF_1%%countFilesFolders% total files/folders %DEF_2%total folders: %countFolders%`r`n`r`n%DEF_3%%countFilesFolders% files/folders:`r`n`r`n%FileFolderList%`r`n ControlSetText, Edit1, %DEF_msg%, ahk_pid %Npid% DEF_1 = found inside`n`n`t%targetFolderEFLocation%`n`n ifInString, selectionEF, 2 msgbox, 4097, DeleteEmptyFolders Utility, 0 empty folders of %countFolders% total were %DEF_1%time: %timeTaken% sec`n`n else msgbox, 4097, DeleteEmptyFolders Utility, 0 empty folders of %countFilesFolders% total files/folders were %DEF_1%total folders: %countFolders%`n`ntime: %timeTaken% sec`n`n } } else { Run, notepad,,, Npid WinActivate, ahk_pid %Npid% WinWaitActive, ahk_pid %Npid% FormatTime, DEF_TimeString GoSub DEF_EditorMsgStrings ControlSetText, Edit1, %DEF_msg%, ahk_pid %Npid% DEF_1 = %countEmptyFolders% empty folders of%A_Space% DEF_2 = were found inside`n`n`t%targetFolderEFLocation%`n`n%DEF_EmpSub1% DEF_3 = time: %timeTaken% sec`n`nKeep in mind that some empty folders might be `nused by the operating system, anti-virus, firewall, `nand various utilities, and even spyware.`n`nSave the log in case you are not sure what you are deleting.`n`n`nDo you wish to delete the %countEmptyFolders% empty folders?`n`nThe recycle bin will be bypassed.`n`nhold Ctrl Shift with OK to delete.`n ifInString, selectionEF, 3 msgbox, 4097, DeleteEmptyFolders Utility, %DEF_1%%countFilesFolders% total files/folders %DEF_2%total folders: %countFolders%`n`n%DEF_3% else msgbox, 4097, DeleteEmptyFolders Utility, %DEF_1%%countFolders% total %DEF_2%%DEF_3% ifMsgBox, OK { if ( GetKeyState("Ctrl","p") AND GetKeyState("Shift","p") ) { listToDelete = %emptyFolderList% GoSub DeleteEmpty if countFoldersEmptySubFolders { msgbox, 4097,, %countFoldersEmptySubFolders% folders containing only empty subfolders.`n`n%countTopmostEmptyFolders% topmost folders containing only empty subfolders.`n`n`n`nDo you wish to delete the %countTopmostEmptyFolders% topmost folders?`n`nThis will delete all %countFoldersEmptySubFolders% folders containing only empty subfolders.`n`nThe recycle bin will be bypassed.`n`nhold Ctrl Shift with OK to delete.`n ifMsgBox, OK if ( GetKeyState("Ctrl","p") AND GetKeyState("Shift","p") ) { DEF_1 = 1 listToDelete = %topmostEmptyFoldersList% GoSub DeleteEmpty } } } } } return DeleteEmpty: errorList= errorsOccurred= ;SplashTextOn, 500, 100, DeleteEmptyFolders Utility, now deleting: --- ;WinSet, AlwaysOnTop, Off, DeleteEmptyFolders Utility Loop, Parse, listToDelete, `n, `r { if A_LoopField= BREAK ; ControlSetText, Static1, now deleting item %A_Index%:`n%A_LoopField%, DeleteEmptyFolders Utility FileRemoveDir, %A_LoopField%, 1 ; recurse to remove empty subfolders if ErrorLevel=1 { errorList=%errorList%%A_LoopField%`r`n errorsOccurred=1 msgbox error deleting %A_LoopField%`n`nerrorList=`n`n%errorList% } } ;SplashTextOff if errorsOccurred=1 { ControlSend, Edit1, ^{end}, ahk_pid %Npid% Control, EditPaste, %errorList%, Edit1, ahk_pid %Npid% msgbox The following empty folders could not be deleted:`n`n%errorList% } else { if DEF_1 = 1 { ControlSend, Edit1, ^{end}of folders containing only empty subfolders:`n<none>`n`n, ahk_pid %Npid% msgbox %countEmptyFolders% folders containing only empty subfolders`n`nsuccessfully deleted. } else { ControlSend, Edit1, ^{end}of folders without items:`n<none>`n`n, ahk_pid %Npid% msgbox %countEmptyFolders% folders without items`n`nsuccessfully deleted. ; msgbox may interfere with deletion } } return ; for GoSub. main return is at the top of function. } ;--------------------------- end function ;-------------------------------------------------------