[转自:https://www.cnblogs.com/dskin/p/4606293.html]

C# Winform实现炫酷的透明动画界面
做过.NET Winform窗体美化的人应该都很熟悉UpdateLayeredWindow吧,UpdateLayeredWindow可以实现窗体的任意透明,效果很好,不会有毛边。不过使用这个API之后,会有一个问题就是无法使用普通控件,而且没有Paint消息。为了解决这个问题,有两种方法。

一、使用双层窗体,底层窗体使用UpdateLayeredWindow作为背景,上层窗体用普通窗体,并且可以使用TransparencyKey或者Region来实现去除不需要的窗体内容,让上层窗体能看到底层的窗体。

二、直接单层窗体,使用控件的DrawToBitmap把控件图像绘制到UpdateLayeredWindow的窗体上,这样就可以看到普通控件了。不过这个也有问题:1.控件内容不能自动更新  2.效率低,很多控件使用DrawToBitmap绘制出的图像不完整,甚至绘制不出图像。比如TextBox无法显示光标,WebBrowser无法显示内容。

三、采用DirectUI技术,重写所有基础控件。效果最好,不过工作量巨大。

使用UpdateLayeredWindow时,一般是需要对Bitmap缓存起来,通过设置剪辑区域,局部重绘来提高效率。另外还可以异步重绘,模拟Winform的失效到重绘。

有些人会说为什么不直接用WPF啊,Wpf和Winform各有优缺点,适应不同的场合。Winform相对于使用更简单一些,系统要求更低。当然需要看人的习惯了和擅长的。

UpdateLayeredWindow 基本使用方法:

重写窗体的 CreateParams 属性

1
2
3
4
5
6
7
8
9
protected   override  CreateParams CreateParams
           {
              get
                  {
                 CreateParams cp  =   base .CreateParams;
                 cp.ExStyle  |=   0x00080000 ;  //  WS_EX_LAYERED 扩展样式
                  return  cp;
             }
         }
  

API调用:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
public   void  SetBitmap(Bitmap bitmap,  byte  opacity)
    {
     if  (bitmap.PixelFormat  !=  PixelFormat.Format32bppArgb)
         throw   new  ApplicationException( "位图必须是32位包含alpha 通道" );
 
    IntPtr screenDc  =  Win32.GetDC(IntPtr.Zero);
    IntPtr memDc  =  Win32.CreateCompatibleDC(screenDc);
    IntPtr hBitmap  =  IntPtr.Zero;
    IntPtr oldBitmap  =  IntPtr.Zero;
 
     try 
         {
        hBitmap  =  bitmap.GetHbitmap(Color.FromArgb( 0 ));   // 创建GDI位图句柄,效率较低
        oldBitmap  =  Win32.SelectObject(memDc, hBitmap);
 
        Win32.Size size  =   new  Win32.Size(bitmap.Width, bitmap.Height);
        Win32.Point pointSource  =   new  Win32.Point( 0 ,  0 );
        Win32.Point topPos  =   new  Win32.Point(Left, Top);
        Win32.BLENDFUNCTION blend  =   new  Win32.BLENDFUNCTION();
        blend.BlendOp              =  Win32.AC_SRC_OVER;
        blend.BlendFlags           =   0 ;
        blend.SourceConstantAlpha  =  opacity;
        blend.AlphaFormat          =  Win32.AC_SRC_ALPHA;
 
        Win32.UpdateLayeredWindow(Handle, screenDc,  ref  topPos,  ref  size, memDc,  ref  pointSource,  0 ,  ref  blend, Win32.ULW_ALPHA);
    }
     finally 
         {
        Win32.ReleaseDC(IntPtr.Zero, screenDc);
         if  (hBitmap  !=  IntPtr.Zero)
              {
            Win32.SelectObject(memDc, oldBitmap);
             
            Win32.DeleteObject(hBitmap);
        }
        Win32.DeleteDC(memDc);
    }
}
  

API声明:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
class  Win32
    {
     public   enum  Bool
        {
        False  =   0 ,
        True
    } ;
 
 
    [StructLayout(LayoutKind.Sequential)]
     public   struct  Point
         {
         public  Int32 x;
         public  Int32 y;
 
          public  Point(Int32 x, Int32 y) 
          {  this .x  =  x;  this .y  =  y; }
    }
 
 
    [StructLayout(LayoutKind.Sequential)]
     public   struct  Size
         {
         public  Int32 cx;
         public  Int32 cy;
 
          public  Size(Int32 cx, Int32 cy) 
            {  this .cx  =  cx;  this .cy  =  cy; }
    }
 
 
    [StructLayout(LayoutKind.Sequential, Pack  =   1 )]
     struct  ARGB
        {
         public   byte  Blue;
         public   byte  Green;
         public   byte  Red;
         public   byte  Alpha;
    }
 
 
    [StructLayout(LayoutKind.Sequential, Pack  =   1 )]
     public   struct  BLENDFUNCTION
         {
         public   byte  BlendOp;
         public   byte  BlendFlags;
         public   byte  SourceConstantAlpha;
         public   byte  AlphaFormat;
    }
 
 
     public   const  Int32 ULW_COLORKEY  =   0x00000001 ;
     public   const  Int32 ULW_ALPHA  =   0x00000002 ;
     public   const  Int32 ULW_OPAQUE  =   0x00000004 ;
 
     public   const   byte  AC_SRC_OVER  =   0x00 ;
     public   const   byte  AC_SRC_ALPHA  =   0x01 ;
 
 
    [DllImport( " user32.dll " , ExactSpelling  =   true , SetLastError  =   true )]
     public   static   extern  Bool UpdateLayeredWindow(IntPtr hwnd, IntPtr hdcDst,  ref  Point pptDst,  ref  Size psize, IntPtr hdcSrc,  ref  Point pprSrc, Int32 crKey,  ref  BLENDFUNCTION pblend, Int32 dwFlags);
 
    [DllImport( " user32.dll " , ExactSpelling  =   true , SetLastError  =   true )]
     public   static   extern  IntPtr GetDC(IntPtr hWnd);
 
    [DllImport( " user32.dll " , ExactSpelling  =   true )]
     public   static   extern   int  ReleaseDC(IntPtr hWnd, IntPtr hDC);
 
    [DllImport( " gdi32.dll " , ExactSpelling  =   true , SetLastError  =   true )]
     public   static   extern  IntPtr CreateCompatibleDC(IntPtr hDC);
 
    [DllImport( " gdi32.dll " , ExactSpelling  =   true , SetLastError  =   true )]
     public   static   extern  Bool DeleteDC(IntPtr hdc);
 
    [DllImport( " gdi32.dll " , ExactSpelling  =   true )]
     public   static   extern  IntPtr SelectObject(IntPtr hDC, IntPtr hObject);
 
    [DllImport( " gdi32.dll " , ExactSpelling  =   true , SetLastError  =   true )]
     public   static   extern  Bool DeleteObject(IntPtr hObject);
 
    [DllImport( " user32.dll " , EntryPoint  =   " SendMessage " )]
     public   static   extern   int  SendMessage( int  hWnd,  int  wMsg,  int  wParam,  int  lParam);
    [DllImport( " user32.dll " , EntryPoint  =   " ReleaseCapture " )]
 
     public   static   extern   int  ReleaseCapture();
     public   const   int  WM_SysCommand  =   0x0112 ;
     public   const   int  SC_MOVE  =   0xF012 ;
 
     public   const   int  SC_MAXIMIZE  =   61488 ;
     public   const   int  SC_MINIMIZE  =   61472 ;
}
  

需要呈现图像的时候调用 SetBitmap 方法。只要优化好,呈现效率比普通的Paint重绘方式高很多,并且不卡不闪烁,支持任意透明。

下面是自己开发出来的效果:

这个是用OpenGL绘制的

推荐一款C#界面库:DSkin界面库(Winform平台首个DirectUI界面库)  http://d.cskin.net

还有一个也是我开发的免费界面库LayeredSkin http://bbs.cskin.net/forum-56-1.html 也可以实现很多效果
 
Winform也可以很炫丽的!
标签: Winform, .NET, C#, UpdateLayeredWindow, 控件美化, 窗体美化, 控件库, Winform美化

[转自:https://www.cnblogs.com/dskin/p/4606293.html] C# Winform实现炫酷的透明动画界面 做过.NET Winform窗体美化的人应该都很熟悉U相关推荐

  1. C#之Action和Func的用法(转自 https://www.cnblogs.com/LipeiNet/p/4694225.html)

    以前我都是通过定义一个delegate来写委托的,但是最近看一些外国人写的源码都是用action和func方式来写,当时感觉对这很陌生所以看起源码也觉得陌生,所以我就花费时间来学习下这两种方式,然后发 ...

  2. 基于dsp_builder的算法在FPGA上的实现(转自https://www.cnblogs.com/sunev/archive/2012/11/17/2774836.html)...

    一.摘要 结合dsp_builder.matlab.modelsim和quartus ii等软件完成算法的FPGA实现. 二.实验平台 硬件平台:DIY_DE2 软件平台:quartus ii9.0 ...

  3. selector是在文件夹drawable中进行定义的xml文件转载 https://www.cnblogs.com/fx2008/p/3157040.html...

    获取Drawable对象: Resources res = mContext.getResources(); Drawable myImage = res.getDrawable(R.drawable ...

  4. 全面理解Javascript闭包和闭包的几种写法及用途--转载自https://www.cnblogs.com/yunfeifei/p/4019504.html...

    全面理解Javascript闭包和闭包的几种写法及用途 好久没有写博客了,过了一个十一长假都变懒了,今天总算是恢复状态了.好了,进入正题,今天来说一说javascript里面的闭包吧!本篇博客主要讲一 ...

  5. Topshelf:一款非常好用的 Windows 服务开发框架 转发https://www.cnblogs.com/happyframework/p/3601995.html...

    背景 多数系统都会涉及到"后台服务"的开发,一般是为了调度一些自动执行的任务或从队列中消费一些消息,开发 windows service 有一点不爽的是:调试麻烦,当然你还需要知道 ...

  6. python自定义分页器()转自https://www.cnblogs.com/yuanchenqi/articles/7652353.html

    """ 分页组件使用示例:obj = Pagination(request.GET.get('page',1),len(USER_LIST),request.path_i ...

  7. 转载 1-EasyNetQ介绍(黄亮翻译) https://www.cnblogs.com/HuangLiang/p/7105659.html

    EasyNetQ 是一个容易使用,坚固的,针对RabbitMQ的 .NET API. 假如你尽可能快的想去安装和运行RabbitMQ,请去看入门指南. EasyNetQ是为了提供一个尽可能简洁的适用与 ...

  8. centons7编译安装zabbix3.4【转https://www.cnblogs.com/kowloon/p/7771495.html】

    或者参考官方文档:https://www.zabbix.com/documentation/3.4/manual/installation/install 一.预编译环境准备 1.lamp安装和启动 ...

  9. GET和POST两种基本请求方法的区别(截取自https://www.cnblogs.com/logsharing/p/8448446.html)

    GET和POST是HTTP请求的两种基本方法,要说它们的区别,接触过WEB开发的人都能说出一二. 表单提交中get和post方式的区别有5点 1.get是从服务器上获取数据,post是向服务器传送数据 ...

  10. 如何优化页面的响应速度 以及如何减少项目初次加载时间(转https://www.cnblogs.com/MarcoHan/p/5295398.html)...

    Web前端性能优化--如何提高页面加载速度 前言:  在同样的网络环境下,两个同样能满足你的需求的网站,一个"Duang"的一下就加载出来了,一个纠结了半天才出来,你会选择哪个?研 ...

最新文章

  1. 七个算法小仙女,写出一本1200页的深度学习技术手册!(限时公开下载)
  2. 浅谈进程同步和互斥的概念
  3. php 分页类使用,php 分页类
  4. DeskArtes 3Data Expert Ultimate中文版
  5. Vmware安装Centos7上网问题的解决
  6. BZOJ3597 SCOI2014方伯伯运椰子(分数规划+spfa)
  7. 中国风喜庆传统新年元旦海报PSD分层模板
  8. 【信息系统项目管理师】知识框架
  9. Python监控屏幕并截图保存
  10. grafa导出数据图标_第5章 数据与可视化 - Grafana与数据可视化 - 《Prometheus操作指南》 - 书栈网 · BookStack...
  11. 利用selenium 实现对百度图片搜索中的图片的抓取
  12. Ignite分布式的内存数据库简单应用
  13. ALFA机器视觉深度学习外观检测自学习人工智能软件——ocr字符检测
  14. 关于在word中使用分栏符 出现左边没有填完就开始了右边 然后再是左边 然后再右边的解决
  15. 深圳求职指南(2004版)
  16. python求特征值以及特征向量,并且输出最小特征值对应的特征向量
  17. JMeter发送数据到Kafka
  18. Android2.3触摸屏功能详解
  19. Java:Java和C有什么区别?
  20. java aria,ARIA 标签和关系

热门文章

  1. Java8新特性之方法引用
  2. 继续教育自动听课软件_2017继续教育挂机软件下载
  3. K3 Cloud 常用语法及常见异常
  4. 汉字编码-GB2312-GBK-GB18030-Big5
  5. 补偿IIR滤波器引入的延迟
  6. 安卓一键新机_新机速递:vivo S7,如7而至;更有Nokia携手一键直达登场
  7. excel学习-自定义图表颜色(QQ截图+colorpix取色器)
  8. QQ音乐与网易云音乐评测分析
  9. 南京大学2022年计算机考研复试分数线多少
  10. 通俗地理解贝叶斯公式(定理)