如何通过Windows 7幻灯片显示检测壁纸更改?

时间:2011-04-04 11:31:19

标签: .net wpf winapi windows-7 wallpaper

我正在编写一个程序,需要知道桌面壁纸何时发生变化。经过一番搜索,我发现了一个部分解决方案: http://www.neowin.net/forum/topic/567779-net-detect-wallpaper-change/

基本上,它说要听WM_SETTINGCHANGE message,并检查壁纸。不幸的是,当Windows 7壁纸幻灯片显示更改壁纸时,似乎不会发送此消息。事实上,似乎没有任何消息发送到我的应用程序(我唯一一次看到WndProc 获取常量消息:))。

所以我的问题是,如果没有轮询注册表和壁纸文件进行更改,有没有办法检测何时发生这种情况?有谁知道我在哪里可以找到列出调用哪个函数的API文档?

3 个答案:

答案 0 :(得分:2)

实际上我找到了解决这个问题的方法。实际上有一个注册表通知机制,因此可以在指定的键/值更改时引发事件。 HKEY_CURRENT_USER\Control Panel\Desktop\Wallpaper是关键。幻灯片显示更改壁纸时,这不会更改,但该位置的文件确实会更改。通过监视文件的更改,您可以实际收到此更改的通知。

顺便说一句,我编写的应用程序的重点都依赖于它,所以省略它不是一个选项:)。

感谢您的回复 - 帮助我的良心休息,不得不经历如此迂回的做事方式。

答案 1 :(得分:1)

这是一个很好的问题,我有一段时间没有回答,看看是否有人知道我不知道的事情。

但不幸的是,我认为你会发现收到与此事件相对应的通知消息是不可能的。壁纸幻灯片显示实际上不会更改系统主题或任何系统设置,因此不会发送WM_SETTINGCHANGE消息。它旨在在后台发生,不要求通知任何应用程序。如果用户选择了“幻灯片放映”选项,则可以合理地假设他们期望定期更改背景,不需要任何交互或通知。简而言之,在至少99%的情况下,由于幻灯片显示选项产生的壁纸更改,您的应用程序会有任何不同的响应。

我能想到的最好的事情是确定他们指定的壁纸应该更改的间隔,然后让应用程序在该时间过后做出相应的响应。基本上,您必须创建并回复自己的通知。

不鼓励强烈轮询注册表。这不仅完全没有文档记录,因而在未来的Windows版本(甚至是Windows更新版本)上也有所突破,但它也不是一个可靠的指标。如果有任何替代方案(包括完全省略功能),那就是我要采取的路径。

答案 2 :(得分:1)

我有一个更好的想法,不久之前我写了一个小程序,自动更改我在LogonScreen上的背景,并希望通过自动检测背景上的壁纸并在窗口更改背景时设置相同来改善这一点。所以,我开始调查,发现:

  1. %USERDIR%\ AppData \ Roaming \ Microsoft \ Windows \ Themes - 来自bg和slideshow.ini的当前转码图像的位置,其中包含有关当前主题的一点信息
  2. %USERDIR%\ AppData \ Local \ Microsoft \ Windows \ Themes - 包含此系统上安装的主题的文件夹
  3. 所以,算法如下:

    1. 阅读slideshow.ini并在[幻灯片放映]
    2. 下获取值
    3. 阅读所有主题文件并比较每个主题的[幻灯片]值,如果相等 - 我们找到当前主题文件
    4. 来自当前主题的文件读取值Interval = 1800000(在我的情况下是30分钟)(BTW,[幻灯片放映]之后的间隔,所以它可以在同一行的迭代中完成)
    5. 从bg上的当前图像读取修改时间:%USERDIR%\ AppData \ Roaming \ Microsoft \ Windows \ Themes \ TranscodedWallpaper.jpg
    6. 因此,我们有时间进行下一次更改(current_time - modify_time + Interval)并且可以在Wallpaper更改时执行任何代码(如果设置已更改或更改被禁用,也不要忘记捕获情况 - 因为它可能会导致异常,因为它会改善我们可以每分钟或类似的事情重新检查这个文件)
    7. 如果您尝试编写相同的程序,请不要忘记压缩图像大小,因为它最多需要256Kb。