viewtopic.php?f=76&t=76056
On modern Windows if you wish to have a folder open in a certain format (explorer view, column sizes, etc) by default you must set it to use a certain "Template" (in Windows 10 you "Customize" your folder). You can config how your templates look, but you can't create new ones, so you're limited to 5 templates (but that's the least of the problems as we shall see). Here are some good references on how to make use of templates:
https://www.tenforums.com/tutorials/7923-change-folder-template-windows-10-a.html
https://www.tenforums.com/tutorials/35093-apply-folder-view-all-folders-same-type-windows-10-a.html
So far so good, but if you actually give it a try and a closer look you'll run into some concerning problems. First let's look deeper on how this template thing work, MS Windows stores the information about the folder on registry, this information is referred as "ShellBag", which is troublesome (1) from the usability aspect as it slowdown explorer, bloat the registry and it limits the amount of custom folders (see BagMRU size); (2) from the privacy aspect you're producing a lot of unnecessary info which is against your interest (and here I believe lies the reason why MS took such stupid rout to folder customization - they want that info registered). More sources to better understand the matter here:
BagMRU size (vs speed ...)
https://techjourney.net/fix-windows-not-remember-save-folder-types-or-folder-views-setting-increase-bagmru-size-cache-memory-size/
https://www.elevenforum.com/t/increase-folder-view-settings-cache-memory-size-in-windows-11.1277/
Forensics
https://ericmathison.com/blog/remove-shellbags-in-windows-for-privacy
https://www.sciencedirect.com/science/article/pii/S1742287609000413
Okay, I think you got the picture about the issue, now let's talk about the solution and here's where AHK comes into play. If using templates isn't an option for a reason (because you keep reaching the max BagMRU limit, or is a privacy minded individual, or simply find it painfully stupid), then I'd advise you to:
- configure the 5 templates (columns and all the stuff)
- clean Shellbags (ShellbagAnalyzerCleaner)
- set BagMRU max size to 1 ("BagMRU Size"=dword:00000001)
- set all folder to default to Documents template or any template that just lists files (I like details view) instead of showing thumbs, that's important as thumbs take ages to load on crowded folders (All_Folders_Use_Documents_Folder_Template.bat)
- have AHK script run on startup with code below (will read a file within the folder to determine the view)
Now I'm gonna share some code to make that work. That's my Frankenstein take on it, but I'm all ears for better solutions/improvements.
First we need a shell hook to trigger the view change, something like this:
Code: Select all
Gui +LastFound
hWnd := WinExist()
DllCall( "RegisterShellHookWindow", UInt,hWnd )
MsgNum := DllCall( "RegisterWindowMessage", Str,"SHELLHOOK" )
OnMessage( MsgNum, "ShellMessage" )
Return ; // End of Auto-Execute Section //
ShellMessage( wParam,lParam )
{
If ( wParam = 6 || wParam = 1 ) ; HSHELL_REDRAW or HSHELL_WINDOWCREATED
{
WinGetClass, this_class, ahk_id %lParam%
if this_class = CabinetWClass
{
exphWnd := WinActive("ahk_class CabinetWClass")
ExplorerViewChange_Window(exphWnd)
}
else if this_class = ExploreWClass
{
exphWnd := WinActive("ahk_class ExploreWClass")
ExplorerViewChange_Window(exphWnd)
}
}
}
Code: Select all
ExplorerViewChange_Window(explorerHwnd)
{
if (!explorerHwnd)
return
Windows := ComObjCreate("Shell.Application").Windows
for window in Windows
{
if (window.hWnd == explorerHwnd)
{
sFolder := window.Document
Folder_Path := window.Document.Folder.Self.Path
IfExist, %Folder_Path%\!cf.txt
{
CF_File = %Folder_Path%\!cf.txt
New_View := ""
FileReadLine, New_View, %CF_File%, 1
if (New_View == "Tiles")
sFolder.CurrentViewMode := 6 ; Tiles
else if (New_View == "Details")
sFolder.CurrentViewMode := 4 ; Details
else if (New_View == "List")
sFolder.CurrentViewMode := 3 ; List
else if (New_View == "Icons_16") {
sFolder.CurrentViewMode := 2 ; Small icons
sFolder.IconSize := 16 ; Actually make the icons small...
} else if (New_View == "Icons_48") {
sFolder.CurrentViewMode := 1 ; Icons
sFolder.IconSize := 48 ; Medium icon size
} else if (New_View == "Icons_96") {
sFolder.CurrentViewMode := 1 ; Icons
sFolder.IconSize := 96 ; Large icon size
} else if (New_View == "Icons_256") {
sFolder.CurrentViewMode := 1 ; Icons
sFolder.IconSize := 256 ; Extra large icons
}
}
}
}
}
Code: Select all
#If (cf_hWnd := WinActive("ahk_class CabinetWClass"))
NumpadMult::
ControlGetFocus, current_control, A
if(current_control = "DirectUIHWND3")
{
cf_path := Explorer_GetPath(cf_hWnd) . "\!cf.txt"
IfExist, %cf_path%
{
CF_View := ""
FileReadLine, CF_View, %cf_path%, 1
if (CF_View == "Tiles")
Default_View := 1
else if (CF_View == "Details")
Default_View := 2
else if (CF_View == "Icons_96")
Default_View := 3
else if (CF_View == "Icons_256")
Default_View := 4
else
Default_View := 2
}
Else
{
Default_View := 2
}
Gui, New,, Customize Folder
Gui, Add, Text,, Choose View:
Gui, Add, Checkbox, X+71 vRecurse, Recurse?
; Gui, Add, DropDownList, w200 Xs0 vChoosen_View Choose%Default_View%, Tiles|Details|List|Icons_16|Icons_48|Icons_96|Icons_256
Gui, Add, DropDownList, w200 Xs0 vChoosen_View Choose%Default_View%, Tiles|Details|Icons_96|Icons_256
Gui, Add, Button, Default Xs75 Y+10 w55, Criar_CF
Gui, Show
ControlFocus, ComboBox1, Customize Folder
return
ButtonCriar_CF:
Gui, Submit
WinActivateBottom, ahk_id %cf_hWnd%
WinWaitActive, ahk_id %cf_hWnd%
mod_date_new = 0
FileGetTime, mod_date_old, %cf_path%
FileSetAttrib, -H, %cf_path%, 0, 0
file := FileOpen(cf_path, "w")
file.Write(Choosen_View)
file.Close()
FileSetAttrib, +H, %cf_path%, 0, 0
if(Recurse == True)
{
cf_upper_path := ParentFolder(cf_path,1)
Loop, Files, % cf_upper_path "\*", DR
{
cf_subs_path := A_LoopFileFullPath . "\!cf.txt"
FileSetAttrib, -H, %cf_subs_path%, 0, 0
file := FileOpen(cf_subs_path, "w")
file.Write(Choosen_View)
file.Close()
FileSetAttrib, +H, %cf_subs_path%, 0, 0
}
}
FileGetTime, mod_date_new, %cf_path%
stop_while := 0
while (mod_date_new <= mod_date_old && stop_while <= 32)
{
Sleep, 62.5
stop_while := stop_while+1
}
Send {F5}
return
}
else
Send *
#If
return
Code: Select all
#If (cf_hWnd := WinActive("ahk_class CabinetWClass"))
Capslock & Space::
Gui, New,, Folder Creator
Gui, Add, Text,, Num Folders:
Gui, Add, Edit, w200 Xs0 vnum_folders gNum_Folders_Check_Length ; Gui, Add, Edit, Number w200 Xs0 vnum_folders gNum_Folders_Check_Length
Gui, Add, Text,, Choose View:
; Gui, Add, DropDownList, w200 Xs0 vChoosen_View Choose2, Tiles|Details|List|Icons_16|Icons_48|Icons_96|Icons_256
Gui, Add, DropDownList, w200 Xs0 vChoosen_View Choose2, Tiles|Details|Icons_96|Icons_256
Gui, Add, Button, Default Xs75 Y+10 w55, Criar_Dirs
Gui, Show
return
Num_Folders_Check_Length:
Gui, Submit, NoHide
if (RegExMatch(%A_GuiControl%, "[0-9]+") && StrLen(%A_GuiControl%) = 3)
Tab_Macro(1)
return
ButtonCriar_Dirs:
Gui, Submit
WinActivateBottom, ahk_id %cf_hWnd%
WinWaitActive, ahk_id %cf_hWnd%
; Template_Pictures := A_ScriptDir . "\Templates\Pictures"
Upper_Dir := Explorer_GetPath()
if(num_folders = "")
num_folders := 1
if(!RegExMatch(num_folders, "[0-9]+"))
{
num_folders := RegExReplace(num_folders, "[\\/:*?""<>|]", "_")
FileCreateDir, %Upper_Dir%\%num_folders%
cf_path := Upper_Dir . "\" . num_folders . "\!cf.txt"
FileSetAttrib, -H, %cf_path%, 0, 0
file := FileOpen(cf_path, "w")
file.Write(Choosen_View)
file.Close()
FileSetAttrib, +H, %cf_path%, 0, 0
}
else if(num_folders > 0 && num_folders <= 1000) ; 1 to 1000 so folders 000 to 999
{
Loop, %num_folders%
{
formated_num_folders := Format("{1:03}", A_Index - 1 )
if !FileExist("%Upper_Dir%\%formated_num_folders%")
{
FileCreateDir, %Upper_Dir%\%formated_num_folders%
; FileCopyDir, %Template_Pictures%, %Upper_Dir%\%formated_num_folders%
; FileMoveDir, %Template_Pictures%, %Upper_Dir%\%formated_num_folders%, 0
cf_path := Upper_Dir . "\" . formated_num_folders . "\!cf.txt"
FileSetAttrib, -H, %cf_path%, 0, 0
file := FileOpen(cf_path, "w")
file.Write(Choosen_View)
file.Close()
FileSetAttrib, +H, %cf_path%, 0, 0
}
}
}
return
; Return
#If
Code: Select all
ParentFolder(filepath,n)
{
FoundPos := InStr(filepath, "\", 0, 0, n) ; Reverse search \ position of n ocurrence
parentpath := SubStr(filepath, 1 , FoundPos-1)
Return parentpath
}
https://www.autohotkey.com/board/topic/80644-how-to-hook-on-to-shell-to-receive-its-messages/
viewtopic.php?f=6&t=35041