C# Windows.Net:获取直接壁纸参考/指针[包括一种快速更改壁纸的方法]

C# Windows.Net:获取直接壁纸参考/指针[包括一种快速更改壁纸的方法],c#,c++,.net,windows,wallpaper,C#,C++,.net,Windows,Wallpaper,我正在尝试在Mono/.Net中为Windows 7/8创建交互式桌面墙纸。我只在墙纸更改时更新墙纸,我使用user32.dll中的SystemParametersInfo()来更新墙纸。我的代码如下所示: const int SPI_SETDESKWALLPAPER = 20; const int SPIF_UPDATEINIFILE = 0x01; const int SPIF_SENDWININICHANGE = 0x02; [DllImport("user32.dll", CharSe

我正在尝试在Mono/.Net中为Windows 7/8创建交互式桌面墙纸。我只在墙纸更改时更新墙纸,我使用user32.dll中的SystemParametersInfo()来更新墙纸。我的代码如下所示:

const int SPI_SETDESKWALLPAPER = 20;
const int SPIF_UPDATEINIFILE = 0x01;
const int SPIF_SENDWININICHANGE = 0x02;

[DllImport("user32.dll", CharSet = CharSet.Auto)]
static extern int SystemParametersInfo(int uAction, int uParam, string lpvParam, int fuWinIni);

public static void Set2(string path)
{
    SystemParametersInfo(SPI_SETDESKWALLPAPER,0,path,SPIF_UPDATEINIFILE | 
    SPIF_SENDWININICHANGE);
}
尽管我只是在必要的时候更新它,但我的墙纸仍然感觉非常迟钝。使用秒表,我发现SystemParametersInfo需要大约1秒的时间来重新加载墙纸。使用第二个线程不会使其更具响应性,因为刷新墙纸仍需要相同的时间。这似乎与位图大小无关。仅在路径位置更新图像不会更改墙纸,除非调用SystemParameterInfo

据我所知,user32.dll使用非托管代码,SystemParameterInfo将图像加载到内存中。但是,必须有某种指向它的指针,否则Windows在呈现桌面时将无法再次找到它

长话短说,我想知道是否有可能访问这个指针。我的图像大小没有改变,所以我可以直接覆盖图像,而不用太担心内存分配。这样我就可以避免昂贵的SystemParametersInfo方法

如果我误解了什么,请告诉我,因为对于Windows,我有点不知所措。如果你知道一个需要不安全代码或C++代码的解决方案,那也很好。如有任何意见或讨论,将不胜感激

多谢各位

编辑: 我现在知道是什么导致了经济放缓

SystemParametersInfo(SPI_SETDESKWALLPAPER,0,path,SPIF_UPDATEINIFILE | 
    SPIF_SENDWININICHANGE);
最后一个参数说明是否更新windows ini文件。在这里我发现的所有关于墙纸更改的线程中,这被设置为3,这显然是Windows主ini文件。在这种情况下,如果每秒多次重新加载背景,则应将其设置为0,因为实际图像路径不会更改。 这样做之后,我可以轻松达到100 fps

由于这几乎肯定是StackOverflow上唯一提到这一点的线程,而且我相信其他人也会有兴趣知道这一点(Microsoft Windows Library文档中没有真正解释这一点),因此我将此“发现”添加到标题中,以便人们可以搜索和查找它


现在,这不是解决方案。我仍然对壁纸工作副本的实际内存指针感兴趣。通过使用它,您不需要传递整个图像,而是可以有选择地只更改在帧之间真正更改的图像字节,就像在大多数GUI系统中所做的那样

您确定问题出在位图加载中吗?这可能只是在windows上设置墙纸的方式,实现并不能保证即时设置墙纸。从秒表结果中,我相当确定SystemParametersInfo中包含1秒睡眠。否则,我的结果(范围从1.05秒到1.09秒)对于实际代码来说就太常规了。通常情况下,脚本执行速度在我的系统上相差很大。但这只是一个最好的猜测。这就是为什么我不想使用这种方法来设置墙纸。@vim让我自己更正一下,在进行了很多测试之后,我得到了一些不到1秒的结果,因此睡眠假说似乎被证明是错误的。