您的位置:首页 > 其它

在.NET中实现彩色、动态光标(colored cursor)

2007-08-04 20:51 344 查看
在win32中实现彩色、动态光标是很easy的事情,只要光标文件是彩色的就可以了。在.NET里面实现起来就不是那么直接了,查阅MSDN发现.NET中的Cursor类不支持彩色或动态光标,原文是这样的 “Cursor 类不支持动画光标(.ani 文件),也不支持彩色(而非黑白色光标)”,这的确有点不爽。遇到这类问题,第一反应就是我们的老办法,先上网查查,看能不能找到解决方案。不负所望,在buidu,google上都能找到相关的文章,问题也得已解决。不过所看到页面的解释也不多,于是在此再次根大家一起讨论学习。
好了,我们言归正传,完成一个彩色或动态光标,大约过程是这样的,使用user32.dll提供的LoadCursorFromFile(String fileName)函数得到一个Windows 句柄,把Windows句柄传给Cursor(IntPtr handle)构造函数,得到一个Cursor对象实例后,调用user32.dll提供的DestroyCursor将Windows句柄所占有的资源释放。具体例子见代码:

using System;
using System.Collections.Generic;
using System.Text;
using System.Runtime.InteropServices;
using System.Windows.Forms;
using System.IO;
using System.Reflection;

namespace CursorTest
{
/**//// <summary>
/// 定义一个Form1类型
/// </summary>
public class Form1 : Form
{
/**//// <summary>
/// 导入user32.dll中的LoadCursorFromFile函数,用于加载光标文件,并得到光标句柄
/// </summary>
/// <param name="fileName">光标文件的全名称</param>
/// <returns>光标句柄</returns>
[DllImportAttribute("user32.dll")]
public static extern IntPtr LoadCursorFromFile(String fileName);

/**//// <summary>
/// 导入user32.dll中的DestroyCursor函数,用于销毁光标句柄,清除资源.
/// </summary>
/// <param name="cursorHandle">需要删除的光标句柄</param>
/// <returns></returns>
[DllImportAttribute("user32.dll")]
public static extern uint DestroyCursor(IntPtr cursorHandle);

/**//// <summary>
/// 从光标库中随机得到一个关闭句柄
/// </summary>
public IntPtr RandomCursorHandle
{
get
{
String folder = @"K:\ani";
String[] files = Directory.GetFiles(folder,"*.ani");//获取该目录下的所有的ani文件

Random random = new Random();
Int32 index = random.Next(0, files.Length);

IntPtr handle = LoadCursorFromFile(files[index]);//根据随机生成的index加载一个光标文件
return handle;//返回光标句柄
}
}

public static void Main()
{
Form1 form = new Form1();
form.Cursor = new Cursor(form.RandomCursorHandle);
//应用程序在空闲时会触发Appliction.Idle事件,这样可以看到光标不挺变化的效果,在不停变化时我们得留言光标句柄的资源释放
Application.Idle += new EventHandler(form.OnApplicationIdle);
Application.Run(form);
}

private void OnApplicationIdle(Object sender, EventArgs e)
{
IntPtr handle = this.RandomCursorHandle;
//在该Cursor(handle)函数中,MSDN中有这么一句话“处理完光标句柄后必须将其释放”
//因此,我们在构造完Cursor对象后,将handle释放。
this.Cursor = new Cursor(handle);

//若不释放在运行过程中,通过任务管理器,发现改程序进程所占有的GDI对象数一直上升,到大9999后,程序将无法运行。
DestroyCursor(handle);

//比较奇怪的是,下面这个语句返回的是true,按照DestroyCursor的意思是销毁该光标句柄所使用的资源,
//但是执行完DestoryCursor后光标还能够正常显示?
System.Console.WriteLine(this.Cursor.Handle == handle);
}

}
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: