转自:http://www.edu1995.com/jysy/ReadNews.asp?TypeId=16&NewsId=617
用C#实现动态桌面墙纸
发表日期:2009年4月27日编辑:
四川省卫生学校(610100) 陈建丽
摘要 本文主要通过运用C#语言Bitmap类的Clone和Save方法,以及API函数SystemParametersInfo,实现了动态修改当前桌面墙纸文件和动态移动大于桌面的墙纸文件两大功能,从而克服了需要用户手工改变桌面墙纸文件和桌面墙纸文件只能静态显示的缺点,使得用户的桌面更加生动和美观。
关键词 桌面 墙纸 动态 C#语言
常言道:爱美之心,人皆有之。因此,很多人都喜欢到网络上找一些好看的图片作为自己电脑的桌面墙纸。但是在使用的过程中往往会发现以下两个问题:1、每次都必须自己手工更改当前的墙纸文件,非常麻烦。2、图片的大小不一定都和桌面的大小一致,不管是选择居中、平铺还是拉伸方式都显得不是那么好看。基于此,设计了下面的这个程序:一是可以定时改变桌面墙纸的图片文件,二是可以将大于桌面大小的图片往上、往左或往左上方进行移动。下面就是具体的实现过程和相关信息的解释说明。
一、启动MicrosoftVisual Studio 2005,选择命令“文件-新建-项目”,在“新建项目”对话框中选择项目类型为“Visual C#---Windows---Windows应用程序”并设置项目名称为DynamicWallPaper。
二、在默认窗体Form1上添加如下表所示控件,并设置相应的属性,最后窗体界面如下图所示。
控件 | 属性名称 | 属性值 | 说明 |
Label | Name | LabelTime | 显示提示信息 |
Text | 更换墙纸的间隔时间(分钟) | ||
NumericUpDown | Name | HowLongChangeWallPaper | 设置更换墙纸的时间间隔 |
Maximum | 10 | 更换墙纸的最大时间间隔 | |
Minimum | 1 | 更换墙纸的最小时间间隔 | |
Button | Name | btnBrowse | 通过该按钮可将对应文件夹中的图片文件加入列表 |
Text | 添加图片所在文件夹(&B) | ||
Button | Name | btnApply | 通过该按钮可以使得设置的更换时间起作用 |
Text | 应用当前所作修改(&A) | ||
ListBox | Name | listBoxPictureFile | 显示可以作为墙纸的文件 |
FolderBrowserDialog | Name | FolderBrowserForPicture | 显示”浏览文件夹”对话框 |
Timer | Name | timerChangeCurrentWallPa | 定时改变当前的墙纸文件 |
Timer | Name | timerMoveWallPaper | 定时移动当前的墙纸文件 |
InterVal | 1000 | 每1秒钟移动一次 |
三、在程序中加入以下引用和代码。当然,其中的注释信息在程序中可以省略。
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using Microsoft.VisualBasic;//添加引用,为了使用文件操作的相关方法(同时要通过菜单命令"项目-添加引用-Microsoft.VisualBasic")
using System.Runtime.InteropServices;//为了使用API
using Microsoft.Win32;//为了使用注册表的相关方法
namespace dynamicwallpaper
{
public partial class Form1 : Form
{
[DllImport("user32.dll", CharSet = CharSet.Auto)]
public static extern int SystemParametersInfo(int uAction, int uParam, string lpvParam, int fuWinIni); //该API可用于设置桌面墙纸
//以下3个为SystemParametersInfo设置墙纸时用常量
public const int SPI_SETDESKWALLPAPER = 20; //设置桌面墙纸
public const int SPIF_UPDATEINIFILE = 1; //将新的参数写入用户Profile文件
public const int SPIF_SENDWININICHANGE = 2;//广播WM_SETTINGCHANGE消息
public int FileWidth;//图像文件的宽度
public int FileHeight;//图像文件的高度
public int CurrX;//显示在屏幕上的图像文件左上角的X坐标
public int CurrY;//显示在屏幕上的图像文件左上角的Y坐标
public int CurrentPictureFileIndex;//存放当前显示的图像文件的Index号
public Boolean HaveShown;//当前墙纸的显示过程是否已经结束
public Form1()
{
InitializeComponent();
}
private void btnBrowse_Click(object sender, EventArgs e)//打开"浏览文件夹"对话框,将选定文件夹中的图片文件添加到列表框中
{
string TempStr;//临时变量:用于保存文件名
Boolean BeenAdded;//临时变量:判断当前文件是否已经加入列表框中
TempStr = "";
FolderBrowserForPicture.ShowDialog();
if (FolderBrowserForPicture.SelectedPath!= "")//选择了文件夹
{
TempStr =
Microsoft.VisualBasic.FileSystem.Dir(FolderBrowserForPicture.SelectedPath + "\\*.*", Microsoft.VisualBasic.FileAttribute.Directory);
while (TempStr != null)//该文件夹有文件
{
if (((TempStr.Substring(TempStr.LastIndexOf
(".")).ToUpper())==".BMP")|| ((TempStr.Substring(TempStr.LastIndexOf
(".")).ToUpper())==".GIF") || ((TempStr.Substring(TempStr.LastIndexOf
(".")).ToUpper())==".JPG") || ((TempStr.Substring(TempStr.LastIndexOf
(".")).ToUpper())==".JPEG"))//如果为常见的图像文件
{
//下面判断该文件是否已经在列表框中
BeenAdded = false;
if (listBoxPictureFile.Items.Count >= 1)//列表框中有文件名
{
for (int j = 1; j <= listBoxPictureFile.Items.Count; j++)
{
if (listBoxPictureFile.Items[j - 1].ToString() == FolderBrowserForPicture.SelectedPath + "\" + TempStr)
{
BeenAdded = true;//已经在列表框中
break;
}
}
}
if (!BeenAdded)//还没有加入列表框中
{
listBoxPictureFile.Items.Add(FolderBrowserForPicture.SelectedPath + "\" + TempStr);//将其加入列表框中
}
}
TempStr = Microsoft.VisualBasic.FileSystem.Dir();//继续查找下一个文件
}
}
}
private void Form1_Load(object sender, EventArgs e)//程序启动时设置墙纸的显示方式为“居中”
{
//通过修改注册表实现
RegistryKey TRegKey;
TRegKey = Registry.CurrentUser.OpenSubKey("Control Panel\\Desktop", true);
if (TRegKey != null)
{
TRegKey.SetValue("WallpaperStyle", "0");
TRegKey.SetValue("TileWallpaper", "0");
}
timerChangeCurrentWallPaper.Interval = (int)HowLongChangeWallPaper.Value * 1000 * 60;
timerChangeCurrentWallPaper.Enabled = true;
CurrentPictureFileIndex = 0;
HaveShown = true;
}
private void timerChangeCurrentWallPaper_Tick(object sender, EventArgs e)//定时改变当前的墙纸文件
{
//设置列表框中下一个文件为当前的桌面墙纸文件
if (listBoxPictureFile.Items.Count > 0 && HaveShown)
{
if (CurrentPictureFileIndex < listBoxPictureFile.Items.Count - 1)
{
CurrentPictureFileIndex += 1;
}
else
{
CurrentPictureFileIndex = 0;
}
HaveShown = false;
Bitmap tBmp1 = new Bitmap(listBoxPictureFile.Items[CurrentPictureFileIndex].ToString());//根据选择的图像文件建立一个bitmap对象
FileWidth = tBmp1.Width; //获得图片文件的宽度和高度
FileHeight = tBmp1.Height;
if (tBmp1.Width <= Screen.PrimaryScreen.Bounds.Width & tBmp1.Height <= Screen.PrimaryScreen.Bounds.Height)
{//图片的宽度和高度都小于桌面时,则直接显示
SetWallPaper(listBoxPictureFile.Items[CurrentPictureFileIndex].ToString(), 0, 0, tBmp1.Width, tBmp1.Height);
HaveShown = true;
}//否则,启动定时器并进行动态显示
else
{
CurrX = 0; //从图片的左上角开始
CurrY = 0;
timerMoveWallPaper.Enabled = true;//启动定时器
}
tBmp1.Dispose();
}
}
private void timerMoveWallPaper_Tick(object sender, EventArgs e)//定时移动当前的墙纸文件
{
Boolean CanMoveLeft; //图片是否可以左移
Boolean CanmoveUp; //是否可以上移
if (FileWidth - CurrX >= Screen.PrimaryScreen.Bounds.Width)
{//可以左移图片
CanMoveLeft = true;
CurrX += Math.Min(12, FileWidth - CurrX); //每次横向向左最多移动12像素
}
else
{
CanMoveLeft = false;
}
if (FileHeight - CurrY >= Screen.PrimaryScreen.Bounds.Height)
{//可以上移图片
CanmoveUp = true;
CurrY += Math.Min(9, FileHeight - CurrY); //每次纵向向上最多移动9像素
}
else
{
CanmoveUp = false;
}
if (CanMoveLeft == false & CanmoveUp == false)//图片已不能上移和左移
{
timerMoveWallPaper.Enabled = false;//停止定时器
HaveShown = true ;
}
int DisplayPicWidth;//屏幕上显示的图片区域的宽度和高度
int DisplayPicHeight;
if (CurrX + Screen.PrimaryScreen.Bounds.Width <= FileWidth)
{
DisplayPicWidth = Screen.PrimaryScreen.Bounds.Width;
}
else
{
DisplayPicWidth = FileWidth - CurrX;
}
if (CurrY + Screen.PrimaryScreen.Bounds.Height <= FileHeight)
{
DisplayPicHeight = Screen.PrimaryScreen.Bounds.Height;
}
else
{
DisplayPicHeight = FileHeight - CurrY;
}
SetWallPaper(listBoxPictureFile.Items[CurrentPictureFileIndex].ToString(), CurrX, CurrY, DisplayPicWidth, DisplayPicHeight);//调用设置墙纸过程
}
//本段程序的基本原理:使用Bitmap类的Clone和Save方法将图片的指定区域保存为临时文件,再使用SystemParametersInfo将临时文件设置为桌面墙纸。
private void SetWallPaper(string SelectedPicFile, int CurrX, int CurrY, int PicWidth, int PicHeight)
{//将图片文件的指定区域保存为BMP文件,并设置为墙纸文件
Bitmap tBmp1 = new Bitmap(SelectedPicFile);//根据选择的图像文件建立一个Bitmap对象
System.Drawing.Imaging.PixelFormat format = tBmp1.PixelFormat;
Rectangle cloneRect = new Rectangle(CurrX, CurrY, PicWidth, PicHeight);
Bitmap cloneBitmap = tBmp1.Clone(cloneRect, format);//根据源图片文件和指定区域,建立bitmap对象
cloneBitmap.Save("C:\\Temp.bmp", System.Drawing.Imaging.ImageFormat.Bmp);//将bitmap对象保存为BMP文件,因为程序中只能使用BMP图像
SystemParametersInfo(SPI_SETDESKWALLPAPER, 0, "C:\\Temp.bmp", SPIF_UPDATEINIFILE | SPIF_SENDWININICHANGE);//设置为墙纸
tBmp1.Dispose();
}
private void btnApply_Click(object sender, EventArgs e)//应用当前的设置
{
timerChangeCurrentWallPaper.Interval = (int)HowLongChangeWallPaper.Value * 1000 * 60;
timerChangeCurrentWallPaper.Enabled = true;
}
}
}
四、现在运行程序,选择一个文件夹,则该文件夹中所有图片文件将加入列表框中。然后,每隔一段时间,程序会自动改变当前的墙纸文件:如果墙纸图片文件宽度和高度都大于桌面,则可以往左上角移动;如果只是宽度大于桌面,或高度大于桌面,则只能左移或上移;如果图片宽度和高度都小于等于桌面,则静止显示在桌面上。
本程序用C# 2.0语言实现,在Windows XP环境下编译通过。
参考文献
1.Karli Watson等著.杨浩译.Visual C#入门经典.清华大学出版社,2006
2.用VB更换桌面墙纸DIY.http://www.mscto.com/vb/2009020122541_2.html
3.冉林仓.用Visual C#调用Windows API函数.北京机械工业学院研00级,http://www.book52.com/article/sort02/sort0160/info- 13576.html
4.MSDN Library for Visual Studio2005,Microsoft Corp.2005
![](https://img-my.csdn.net/uploads/201205/15/1337070927_8923.png)