WinForm 分屏 [ WinForm | Panel | 视频监控分屏 ]

简介:

前言
      视频监控的分屏技术实际上就是通过动态Panel + 动态指定其Location和Size来实现的,还需要一个计算分屏数目的算法,本文将弥补视频监控系列中动态分屏的功能,权当续文吧 : )

正文
      1.      先“上菜”再讲做法:——上图~~
 

 

 

 

 2.      动态Panel
 

         ///   <summary>
        
///  动态创建面板
         
///   </summary>
        
///   <param name="xy"> Panel的XY坐标 </param>
        
///   <param name="wh"> Panel的大小 </param>
         private  Panel CreatePanel(Point xy, Size wh)
        {
            Panel panel 
=   new  Panel();
            panel.BackColor 
=  System.Drawing.Color.Transparent;
            panel.BackgroundImageLayout 
=  System.Windows.Forms.ImageLayout.Stretch;
            panel.Location 
=  xy;
            panel.Name 
=   string .Concat( " pVideo " );
            panel.Size 
=  wh;
            panel.TabIndex 
=   0 ;
            panel.BackColor 
=  Color.Black;
            
return  panel;
        }

      3.      分屏算法
 

         ///   <summary>
        
///  根据通道数动态计算Panel的坐标和大小
        
///   </summary>
        
///   <param name="channelCount"> 通道数 </param>
        
///   <param name="xy"> 返回运算后每个Panel的坐标 </param>
        
///   <param name="wh"> 返回运算后每个Panel的大小 </param>
         private   void  MathDynamicPanel( int  channelCount,  out  Point[] xy,  out  Size[] wh)
        {
            xy 
=   new  Point[channelCount];
            wh 
=   new  Size[channelCount];

            
// 第一个Panel的起始坐标——不变
            xy[ 0 =   new  Point( 2 38 );

            
// 模数
             int  modulo;

            
if  (channelCount  <=   4 )
                modulo 
=   2 ;
            
else   if  (channelCount  <=   9 )
                modulo 
=   3 ;
            
else   if  (channelCount  <=   16 )
                modulo 
=   4 ;
            
else   if  (channelCount  <=   25 )
                modulo 
=   5 ;
            
else   if  (channelCount  <=   36 )
                modulo 
=   6 ;
            
else   if  (channelCount  <=   49 )
                modulo 
=   7 ;
            
else //  if (channelCount <= 64)
                modulo  =   8 ;

            
int  width, height;
            
// 610 为整个预览区的宽
            width  =  ( 610   -  modulo  *   1 /  modulo;
            
// 532 为整个预览区的高
            height  =  ( 532   -  modulo  *   1 /  modulo;

            
for  ( int  i  =   0 ; i  <  channelCount; i ++ )
            {
                wh[i] 
=   new  Size(width, height);
                
if  (i  >   0 )
                {
                    
// 同一行的Y坐标相等
                    
// 同一列的X坐标相等
                     if  (i  %  modulo  ==   0 )
                        xy[i] 
=   new  Point(xy[i  -  modulo].X, xy[i  -  modulo].Y  +  height  +   1 );
                    
else
                        xy[i] 
=   new  Point(xy[i  -   1 ].X  +  width  +   1 , xy[i  -   1 ].Y);
                }
            }
        }

            代码说明:
                  a).      采用平方算法,即4个头4个Panel(2 ^ 2),8个头9个Panel(3 ^ 3),算是比较简单也满足基本需求的算法了。
                  b).      注意需要固定左上角顶点坐标和总面积,即(2,38)和610,532,这个可以根据自己的时间情况加以修改,可以定义成const int 就行。
                  c).      注意里面算坐标的时候有+1,这个是Panel之间的间隙。
      4.      使用例子
        在Form_Load中加入如下代码:
 

            Point[] xy;
            Size[] wh;
            
int  channel  =   8 ;
            
// 计算面板坐标
            MathDynamicPanel(channel,  out  xy,  out  wh);
            
// 创建面板
             for  ( int  i  =   0 ; i  <  channel; i ++ )
            {
                
this .Controls.Add(CreatePanel(xy[i], wh[i]));
            }

            运行即可见到截图中的样子,最大支持64个屏幕,满足基本需求,自己加上放大、缩小和全屏的代码功能就比较完整了。

 

  5.文章更新维护

    5.1  2010-5-22  修改一下方法,更加好用点

         ///   <summary>
        
///  计算视频面板位置和面积
        
///   </summary>
        
///   <param name="channelCount"></param>
        
///   <param name="TotalSquare"> 总面积和坐标 </param>
        
///   <returns></returns>
         private  IList < Rectangle >  CalcPanelRectangle( int  channelCount, Size TotalArea)
        {
            IList
< Rectangle >  result  =   new  List < Rectangle > ();

            
// 模数
             int  modulo;
            
if  (channelCount  <=   4 )
                modulo 
=   2 ;
            
else   if  (channelCount  >   64 )
                modulo 
=   8 ;
            
else
                modulo 
=  ( int )Math.Ceiling(Math.Sqrt(channelCount));          // 平方根

            
int  width, height;

            
// 单个画面大小
            width  =  (TotalArea.Width  -  modulo  *   1 /  modulo;
            height 
=  (TotalArea.Height  -  modulo  *   1 /  modulo;

            
for  ( int  i  =   0 ; i  <  channelCount; i ++ )
            {
                Rectangle rect 
=   new  Rectangle();
                rect.Width 
=  width;
                rect.Height 
=  height;
                
if  (i  %  modulo  ==   0 )
                {
                    rect.X 
=   1 ;
                    
if  (i  ==   0 )
                        rect.Y 
=   1 ;
                    
else
                        rect.Y 
=  result[i  -  modulo].Y  +  height  +   1 ;
                }
                
else
                {
                    rect.X 
=  result[i  -   1 ].X  +  width  +   1 ;
                    rect.Y 
=  result[i  -   1 ].Y;
                }
                result.Add(rect);
            }
            
return  result;
        }


本文转自over140 51CTO博客,原文链接:http://blog.51cto.com/over140/586624,如需转载请自行联系原作者
相关文章
|
6月前
|
数据采集 监控 网络协议
linux系统中利用QT实现视频监控的基本方法
linux系统中利用QT实现视频监控的基本方法
179 0
|
监控 定位技术 安全
Qt编写安防视频监控系统10-视频轮询
一、前言 视频轮询在视频监控系统中是一个基础的核心功能,尤其是上了大屏以后,这个功能是必须的,根据预先设定的轮询间隔逐个加载视频到预先设定的通道画面数中,轮询间隔、轮询画面数、轮询采用的码流类型(主码流、子码流)都可以在系统设置中进行统一设置,轮询的视频源采用摄像机表中的所有摄像机,当画面数不够的时候,其余留空显示即可,轮询到最后一个视频,重新从第一个开始轮询。
1533 0
|
7月前
|
编解码 监控 物联网
【学员源鑫笔记】韦东山物联网流媒体实战项目-智慧家居视频监控系统(值得收藏)
【学员源鑫笔记】韦东山物联网流媒体实战项目-智慧家居视频监控系统(值得收藏)
427 0
|
计算机视觉
《DeepStream 大规模智能视频分析系统》电子版地址
DeepStream: 大规模智能视频分析系统
71 0
《DeepStream 大规模智能视频分析系统》电子版地址
|
运维 监控 前端开发
视频监控系统供电方式及选择方法
视频监控系统供电方式及选择方法
视频监控系统供电方式及选择方法
|
机器学习/深度学习 存储 边缘计算
SysML 2019论文解读:视频分析系统的提升
SysML 2019 已于 3 月 31 日-4 月 2 日在斯坦福成功举办,本文将解读两篇在高效视频分析方面的研究。
119 0
SysML 2019论文解读:视频分析系统的提升
|
监控 定位技术 安全
Qt编写安防视频监控系统12-异形布局
一、前言 视频监控系统中,除了常规的1画面、4画面、9画面、16画面以外,还有几个布局比较另类,比如6画面、8画面、13画面,有些通道需要占据不同的行列,4画面、9画面、16画面都是非常对称的布局,行数和列数都一样,而且每个通道占据的面积都一样,初学者都知道怎么处理。
1305 0
|
监控 定位技术 安全
Qt编写安防视频监控系统11-动态换肤
一、前言 Qt中的动态换肤技术是非常一流的,直接调用qApp->setStyleSheet(qss);就可以对整个应用程序进行换肤,如果样式表内容不多,或者对应的贴图不对,效率还是蛮好的,不过据说有些人写了几千行的样式表,加载起来能够明显感觉卡顿,毕竟此时全部刷新加载重绘,是非常耗CPU的,这种情况就需要避免尽量统一样式表,能合并的就合并,当然,在性能比较好的电脑上,这个基本上遇不到的,也感觉不到的,好比现在的手机相比于十年前的手机,现在动不动都6GB内存了,比起以前256MB内存的时候,不知道爽了多少倍,软件上已经优化不了的事情,靠硬件升级到来的优化体验还是非常棒的。
1065 0

热门文章

最新文章