透明窗体的实现

今天实现了窗体呈现透明的显示,里面涉及到一些东西,写下来共享,其实很简单,不过以前自己不知道而已。首先创建一个基于对话框的应用程序框架,然后拖进一个Splider和一个edit控件,并分别给相应的空间添加相应的空间变量。这里的edit完全是为了显示用,没有实际的输入功能。主要涉及的代码在OnInitDalogSplider

控件的响应函数中。

然后再OnInitDialog中添加如下的初始化信息

::SetWindowPos(m_hWnd, HWND_TOPMOST, 0, 0, 0, 0, SWP_NOSIZE|SWP_NOMOVE);
	m_slide.SetRange(10, 255);
	m_slide.SetPos(128);
	SetWindowLong(this->GetSafeHwnd(), GWL_EXSTYLE, GetWindowLong(this->GetSafeHwnd(), GWL_EXSTYLE)^0x80000);
	HINSTANCE hInst = LoadLibrary("User32.DLL");
	if(hInst)
	{
		typedef BOOL (WINAPI*MYFUNC)(HWND, COLORREF,BYTE, DWORD);
		MYFUNC fun = NULL;
		fun = (MYFUNC)GetProcAddress(hInst, "SetLayeredWindowAttributes");
		if(fun)
			fun(this->GetSafeHwnd(), 0, 128, 2);
		FreeLibrary(hInst);
	}

 其中主要用到的是SetWindowPos、SetWindowLong、LoadLibrary和Splider控件的一些类内函数,SetWindowPos是一个全局函数,用来设定窗体的位置以及显示方式,SetWindowLong函数用来设定窗口的属性,GetSafeHwnd得到一个对象指针的句柄时,最安全的方法就是用这个函数,函数中的方法就是显示的调用动态链接库,以前没有遇到过。

然后给Splider控件添加Release消息,在响应函数中添加的代码如下:

 1     BYTE eff = (BYTE)m_slide.GetPos();
2 HINSTANCE hInst = LoadLibrary("User32.dll");
3 if(hInst)
4 {
5 typedef BOOL (WINAPI * MYFUNC) (HWND,COLORREF, BYTE, DWORD);
6 MYFUNC fun = NULL;
7 fun = (MYFUNC)GetProcAddress(hInst, "SetLayeredWindowAttributes");
8 if(fun)
9 fun(this->GetSafeHwnd(), 0, eff, 2);
10 FreeLibrary(hInst);
11 }
12 CString str;
13 str.Format("%d", 100 * eff / 255);
14 GetDlgItem(IDC_EDIT1)->SetWindowText(str);

这里也有一个显示调用动态链接库的过程,还涉及到edit的显示,以前弄过,现在忘了,很长时间没有弄过VC了,

下面讲点以前不知道的,第五行的代码一开始没看懂,查了之后才知道这是顶一个函数类型的指针,如下面:

typedef BOOL (WINAPI *ShowLayer)(HWND,COLORREF,BYTE,DWORD); 就是将BOOL WINAPI function(HWND,COLORREF,BYTE,DWORD)这样类型的函数指针定义为ShowLayer ,这个属于一个类型的定义,被定义的类型为函数指针。下面的例子就是一个具体的相似的实例。

#include <stdio.h>
typedef int (*PF)(void*,void*);
int max(int* a,int* b){return *a>*b?*a:*b;}
void main()
{
int (*pf1)(int*,int*),a=5,b=3;
PF   pf2,pf3;
pf1=max;
pf2=(int (*)(void*,void*))max; /*强制类型转换*/
pf3=(PF)max;   /*同样的类型转换*/
printf("max of 5 and 3:  %d",pf1(&a,&b)); putchar('\n');
printf("max of 5 and 3:  %d",pf2(&a,&b)); putchar('\n');
printf("max of 5 and 3:  %d",pf3(&a,&b)); putchar('\n');
}

最后,LoadLibary载入制定的动态链接库,并将它映射到当前的进程使用的地址空间;GetProcAddress检索制定的动态链接库中的输出库函数地址。

原文地址:https://www.cnblogs.com/lscheng/p/2421356.html