I am making a project involving the icons of the folders on my windows desktop. When I change the icon with python, the change doesn't occur immediately. You have to refresh it somehow (for example restart your laptop). And to counter this I searched the internet and found this piece of code from this github page: https://github.com/sunshowers/iconrefresher/blob/master/refresh-icons.py
def update_folder_icon():
# !/usr/bin/env python
# Released to the public domain.
# http://creativecommons.org/publicdomain/zero/1.0/
import ctypes
from ctypes import wintypes
# http://msdn.microsoft.com/en-us/library/ms644950
SendMessageTimeout = ctypes.windll.user32.SendMessageTimeoutA
SendMessageTimeout.restype = wintypes.LPARAM # aka LRESULT
SendMessageTimeout.argtypes = [wintypes.HWND, wintypes.UINT, wintypes.WPARAM, wintypes.LPARAM,
wintypes.UINT, wintypes.UINT, ctypes.c_void_p]
# http://msdn.microsoft.com/en-us/library/bb762118
SHChangeNotify = ctypes.windll.shell32.SHChangeNotify
SHChangeNotify.restype = None
SHChangeNotify.argtypes = [wintypes.LONG, wintypes.UINT, wintypes.LPCVOID, wintypes.LPCVOID]
HWND_BROADCAST = 0xFFFF
WM_SETTINGCHANGE = 0x001A
SMTO_ABORTIFHUNG = 0x0002
SHCNE_ASSOCCHANGED = 0x08000000
SendMessageTimeout(HWND_BROADCAST, WM_SETTINGCHANGE, 0, 0, SMTO_ABORTIFHUNG, 5000, None)
SHChangeNotify(SHCNE_ASSOCCHANGED, 0, None, None)
Everytime I use this code all of the folder icons refresh and blink. I need to use this code very often in my project (as often as every 3 seconds) so it would be nice to not see the blinking effect every single time. So my question is: Is there a way for me to only update one specific folder by for example passing the folder path as a parameter to the update_folder_icon()
function?
Here is the code I use to change the icons of folder:
def set_folder_icon(folder_path, icon_path):
if not os.path.isdir(folder_path):
print("Folder Required To Set The Icon!")
return
shell32 = ctypes.windll.shell32
folder_path = os.path.abspath(folder_path)
icon_path = os.path.abspath(icon_path)
fcs = SHFOLDERCUSTOMSETTINGS()
fcs.dwSize = sizeof(fcs)
fcs.dwMask = FCSM_ICONFILE
fcs.pszIconFile = icon_path
fcs.cchIconFile = 0
fcs.iIconIndex = 0
hr = shell32.SHGetSetFolderCustomSettings(byref(fcs), folder_path, FCS_FORCEWRITE)
if hr:
raise WindowsError(win32api.FormatMessage(hr))
sfi = SHFILEINFO()
hr = shell32.SHGetFileInfoW(folder_path, 0, byref(sfi), sizeof(sfi),
SHGFI_ICONLOCATION)
if hr == 0:
raise WindowsError(win32api.FormatMessage(hr))
shell32.SHUpdateImageW(sfi.szDisplayName, sfi.iIcon, 0, 0)
Other possibly useful information:
- Windows Version: Windows 11
- Python version: 3.8
- IDE: Pycharm
CodePudding user response:
I managed to solve the issue. The issue wasn't really the code itself, it was more like a windows bug. When you set the icon of a folder the first time it works, but when you change the icon again, but the icon file has the same name then the change doesn't happen. So to counter this you either have to do something aggressive like SHCNE_ASSOCCHANGED
or simply use a different icon file name.