Python windows中的图标覆盖不反映在资源管理器中

Python windows中的图标覆盖不反映在资源管理器中,python,windows,explorer,py2exe,shell-icons,Python,Windows,Explorer,Py2exe,Shell Icons,我使用python2.7和py2exe从python脚本创建dll 已成功创建DLL并注册“我的图标覆盖状态”条目,然后通过任务管理器重新启动windows资源管理器进程 验证我的条目是否在注册表中,是的,它在那里 但当我通过python测试应用程序脚本为特定文件夹位置设置状态时 我希望所选路径中的所有文件和文件夹都应该覆盖我的覆盖图标 但不,图标覆盖根本没有发生 但当我通过python脚本测试注册表项(不创建DLL)并通过测试应用程序脚本设置图标覆盖时 是的,它工作得很好 我很困惑,为什么在尝

我使用python2.7和py2exe从python脚本创建dll

已成功创建DLL并注册“我的图标覆盖状态”条目,然后通过任务管理器重新启动windows资源管理器进程

验证我的条目是否在注册表中,是的,它在那里

但当我通过python测试应用程序脚本为特定文件夹位置设置状态时

我希望所选路径中的所有文件和文件夹都应该覆盖我的覆盖图标

但不,图标覆盖根本没有发生

但当我通过python脚本测试注册表项(不创建DLL)并通过测试应用程序脚本设置图标覆盖时

是的,它工作得很好

我很困惑,为什么在尝试使用我的DLL时它不会发生

下面是我注册状态项的python脚本

import os
import win32traceutil
import pythoncom
import winerror
from win32com.shell import shell, shellcon
from multiprocessing.connection import Client

REG_PATH = r'Software\Microsoft\Windows\CurrentVersion\Explorer\ShellIconOverlayIdentifiers'
REG_KEY  = "IconOverlayTest"

class IconOverlay:
    _reg_desc_       = 'Icon Overlay COM Server'
    _public_methods_ = ['GetOverlayInfo', 'GetPriority','IsMemberOf']
    _com_interfaces_ = [shell.IID_IShellIconOverlayIdentifier, pythoncom.IID_IDispatch]
    def __init__(self, *_args, **_kwargs):
        self._icon = None
        self._icon_id = None
        raise NotImplementedError
    def GetOverlayInfo(self):
        return self._icon, 0, shellcon.ISIOI_ICONFILE
    def GetPriority(self):
        return 0
    def IsMemberOf(self, path, _attrs):
        if is_member(path, self._icon_id):
            return winerror.S_OK
        return winerror.E_FAIL

class IconOverlay_test(IconOverlay):
    _reg_progid_     = 'a.TestServer1'
    _reg_clsid_      = '{8B19F050-8354-11E1-A0FE-5C260A5D15E4}'
    def __init__(self):
        self._icon = "C:\\Users\\Administrator\\mat\\icon_overlay\\icons\\1.ico"
        self._icon_id = 101 

classes =   [IconOverlay_test,]

def is_member(path, icon_id):
    try:
        conn = None
        conn = Client("\\\\.\\pipe\\test.listener", "AF_PIPE")
        conn.send(path)
        if conn.poll(3):
            reply   =   conn.recv()
            return reply == icon_id
    except Exception:
        pass
    finally:
        conn and conn.close()
    return False

def DllRegisterServer():
    print("Registering %s ......."%IconOverlay._reg_desc_)
    import winreg
    #winreg = _winreg
    for view in [winreg.KEY_WOW64_64KEY, winreg.KEY_WOW64_32KEY]:
        for cls in classes:
            with winreg.CreateKeyEx(winreg.HKEY_LOCAL_MACHINE, r"%s\%s" %
                    (REG_PATH, cls._reg_progid_), 0,
                    winreg.KEY_ALL_ACCESS|view) as hkey:
                print("    %s"%cls)
                winreg.SetValueEx(hkey, None, 0, winreg.REG_SZ, cls._reg_clsid_)
    print("Registration complete: %s" % IconOverlay._reg_desc_)

def DllUnregisterServer():
    print("Unregistering %s ......."%IconOverlay._reg_desc_)
    import winreg
    #winreg = _winreg
    for view in [winreg.KEY_WOW64_64KEY, winreg.KEY_WOW64_32KEY]:
        for cls in classes:
            try:
                _key = winreg.DeleteKeyEx(winreg.HKEY_LOCAL_MACHINE, r"%s\%s"
                        % (REG_PATH, cls._reg_progid_),
                        winreg.KEY_ALL_ACCESS|view)
            except WindowsError as err:
                if err.errno != 2:
                    raise
    print("Unregistration complete: %s" % IconOverlay._reg_desc_)

if __name__ == '__main__':
    from win32com.server import register
    register.UseCommandLine(*classes,
                            finalize_register = DllRegisterServer,
                            finalize_unregister = DllUnregisterServer)

这真的是很痛苦的工作,祝你好运

我相信windows只允许注册10个不同的图标,并且只允许按字母顺序注册前10个图标。你已经登记了10张了吗?如果您安装了dropbox、tortoise svn等,则很容易超过10,因为每个图像都算作一个条目。如果是这种情况,请尝试在名称前加下划线或0,以确保它具有优先级,尽管这将意味着另一个图标将丢失-我认为没有办法解决这个问题

有时windows不知道刷新图标的状态。您正在运行哪个版本的windows?有些比另一些更糟。我似乎记得XP在这方面不太擅长。虽然有一些技巧可以让它更新,你可以通过WindowsAPI刷新窗口,但是它看起来很可怕,整个浏览器都会闪烁。我发现的一个更好的方法是更改文件上的A属性。这就是我使用的技巧:

import stat,os

file_att= os.stat(path)[0]
if file_att & stat.S_IWRITE:
    os.chmod(path,stat.S_IREAD)
    os.chmod(path,stat.S_IWRITE)
else:
    os.chmod(path,stat.S_IWRITE)
    os.chmod(path,stat.S_IREAD)

我在Windows7中工作。我确保我的应用程序条目首先在注册表中列出,以获得优先级。我的问题是,相同的python脚本在作为脚本进行测试时运行良好,并且相同的脚本被转换为dll,而这些dll在测试时无法正常运行。如果你提示我一些想法,哪里可能是环洞,这将是一个伟大的帮助我实现这一点。给我一个适合你的样品。