快速业务通道

WPF自定义控件——使用Win32控件

作者 佚名技术 来源 NET编程 浏览 发布时间 2012-05-22

本文配套源码

虽然WPF很强大,但是有些东西win32做的已经很好,我们完全可以拿来主义。

一.如何创建一 个win32控件

1.首先定义一个WNDCLASSEX的类,参考 http://baike.baidu.com/view/1750396.html?tp=0_11

WNDCLASSEX wndClsEx = new  WNDCLASSEX();
wndClsEx.Init();//(uint)Marshal.SizeOf(this);得到类的大小
wndClsEx.style = WndClassType.CS_VREDRAW | WndClassType.CS_HREDRAW;//窗口的风格
wndClsEx.lpfnWndProc = new WndProcDelegate(User32Dll.DefWindowProc);//处理类的消息,这 里用的是默认处理
wndClsEx.cbClsExtra = 0;//指定紧跟在窗口类结构后的附加字节数
wndClsEx.cbWndExtra = 0;//如果一个应用程序在资源中用CLASS伪指令注册一个对话框类时,则必 须把这个成员设成DLGWINDOWEXTRA
wndClsEx.hInstance = Kernal32Dll.GetModuleHandle (null);//模块的句柄
wndClsEx.hIcon = IntPtr.Zero;//图标句柄
wndClsEx.hIconSm =  IntPtr.Zero;//和窗口类关联的小图标。如果该值为NULL。则把hCursor中的图标转换成大小合适的小 图标。
wndClsEx.hCursor = IntPtr.Zero;//光标句柄
wndClsEx.hbrBackground =  IntPtr.Zero;//背景画刷句柄
wndClsEx.lpszClassName = m_WndClsName;//定义自己的类名, 比如curry,或XXX
wndClsEx.lpszMenuName = null;//菜单名称

2.注册类,返回 值非0为成功

bool success = User32Dll.RegisterClassEx(ref wndClsEx) !=  0;
Debug.Assert(success, "RegisterWndClass failed.");

3.创建 窗口,参考http://baike.baidu.com/view/1080304.htm

IntPtr windowHandle =  User32Dll.CreateWindowEx(ExtendedWndStyle.WS_EX_LAYOUTRTL//扩展样式
, m_WndClsName  //刚才注册完的名称
, null     //窗体名称
, WndStyle.WS_VISIBLE |  WndStyle.WS_CHILD //子窗体
, this.Left //X坐标
, this.Top //Y 坐标
,  this.Width //宽度
, this.Height //高度
, this.Parent.Handle //父对象句柄
, IntPtr.Zero //上下文菜单句柄
, Kernal32Dll.GetModuleHandle(null)//实例句柄
, IntPtr.Zero//指向一个值的指针,该值传递给窗口 WM_CREATE消息
);
Debug.Assert(User32Dll.IsWindow(windowHandle), "CreateWindowEx  failed.");

如果你想参考其它窗口的样式的信息的话,可以用Spy++这个工具看

4.显示窗口

User32Dll.ShowWindow(windowHandle, (int) (this.Visible ? WindowShowStyle.Show : WindowShowStyle.Hide));

5.销毁窗口 ,注销类

User32Dll.DestroyWindow(windowHandle);
windowHandle =  IntPtr.Zero;

User32Dll.UnregisterClass(m_WndClsName,  Kernal32Dll.GetModuleHandle(null));

二.把Win32控件放到WPF

其实放到WPF中 这个只是视觉的假象,我们的顶级窗口如Window,Popup也都是通过CreateWindowEx创建出来的,(当然菜 单也是CreateWindowEx)所以我们创建的Win32控件的Parent一般都是顶级窗口,IntPtr hwnd = ((HwndSource)PresentationSource.FromVisual(uielement)).Handle; 得到的句柄是顶级窗体的句柄, 因为WPF和GDI+ 的渲染层不一样,两者因为“空域”问题使得像素不能交互,具体的见 http://msdn.microsoft.com/zh-cn/library/aa970688.aspx。

在win32时代有时候把窗体弄成不 规则透明图形时可能会作的事,这里也记录下:参考自 http://www.codeproject.com/KB/dialog/SemiTranDlgWithCtrls.aspx

xp及以上版本中可以使用 UpdateLayeredWindow创建类似PGN图片带ALPHA通道的窗口。

把窗口扩展样式设置为 ExtendedWndStyle.WS_EX_LAYERED |ExtendedWndStyle.WS_E

凌众科技专业提供服务器租用、服务器托管、企业邮局、虚拟主机等服务,公司网站:http://www.lingzhong.cn 为了给广大客户了解更多的技术信息,本技术文章收集来源于网络,凌众科技尊重文章作者的版权,如果有涉及你的版权有必要删除你的文章,请和我们联系。以上信息与文章正文是不可分割的一部分,如果您要转载本文章,请保留以上信息,谢谢!

分享到: 更多

Copyright ©1999-2011 厦门凌众科技有限公司 厦门优通互联科技开发有限公司 All rights reserved

地址(ADD):厦门软件园二期望海路63号701E(东南融通旁) 邮编(ZIP):361008

电话:0592-5908028 传真:0592-5908039 咨询信箱:web@lingzhong.cn 咨询OICQ:173723134

《中华人民共和国增值电信业务经营许可证》闽B2-20100024  ICP备案:闽ICP备05037997号