zoukankan      html  css  js  c++  java
  • C#仿QQ面板的简单实现

    首先来看看最终效果:

    下边我们来一步一步实现:

    首先新建一个C# windows application,并在界面上添加一个Pannel控件,拉成合适的形状,如下图:

    我们要做的,就是将Button加入到Pannel控件中,并根据鼠标点击移动Button和添加子Button.

    第一步,定义一些必要的变量和属性:

            private string[] _Module;
            
    private string[,] _ChildModule;
            
    private int _ModuleButtonHeight = 50;
            
    private int _ChildButtonHeight = 30;

            
    /// <summary>
            
    /// 初始模块
            
    /// </summary>
            public string[] Module
            {
                
    get { return _Module; }
                
    set { _Module = value; }
            }

            
    /// <summary>
            
    /// 初始子模块
            
    /// </summary>
            public string[,] ChildModule
            {
                
    get { return _ChildModule; }
                
    set { _ChildModule = value; }
            }

    其中Module数组和ChildModule数组分别是第一层菜单和第二层菜单的Button的Name,_ModuleButtonHeight_ChildButtonHeight是第一层和第二层菜单的Height.

    定义好相关变量和属性了.我们就开始往Panel里面添加东西了.在Form1_Load里面加入下边的代码:

            private void Form1_Load(object sender, EventArgs e)
            {
                
    this.panel1.BorderStyle = BorderStyle.FixedSingle;
                
    //初始化
                Module = new string[] { "初始模块1""初始模块2""初始模块3" };
                ChildModule 
    = new string[32];
                ChildModule[
    00= "子模块1";
                ChildModule[
    01= "子模块2";
                ChildModule[
    10= "子模块3";
                ChildModule[
    11= "子模块4";
                ChildModule[
    20= "子模块5";
                ChildModule[
    21= "";

                
    for (int i = 0; i < Module.Length; i++)
                {
                    
    //增加模块Button
                    Button btn = new Button();
                    btn.FlatStyle 
    = FlatStyle.Flat;
                    btn.Width 
    = this.panel1.Width;
                    btn.Height 
    = _ModuleButtonHeight;
                    btn.Name 
    = string.Format("Button{0}", i.ToString());
                    btn.Text 
    = Module[i];
                    btn.Top 
    = _ModuleButtonHeight * i;
                    btn.Click 
    += new EventHandler(btn_Click);
                    
    this.panel1.Controls.Add(btn);
                }
            }

    上边代码是根据Module定义的数目往Pannel里面塞Button,这些Button就是第一层的菜单项.当我们点击这些Button的时候,就要显示子菜单项.所以当点击Button的时候触发的事件需要做如下处理:

            private void btn_Click(object sender, EventArgs e)
            {
                
    //标志是否找到用户点击的Button
                bool findOutStatus = false;

                
    //清除上一次操作加载的子菜单项
                for (int i = 0; i < this.panel1.Controls.Count; i++)
                {
                    
    if (this.panel1.Controls[i].GetType().Name == "Panel")
                    {
                        
    this.panel1.Controls.RemoveAt(i);
                    }
                }

                
    for (int i = 0; i < this.panel1.Controls.Count; i++)
                {
                    
    if (this.panel1.Controls[i].GetType().Name == "Button")
                    {
                        
    //重新定义各个button位置
                        if (!findOutStatus)
                        {
                            
    this.panel1.Controls[i].Top = _ModuleButtonHeight * i;
                        }
                        
    else
                        {
                            
    this.panel1.Controls[i].Top = this.panel1.Height - (_ModuleButtonHeight * (Module.Length - i));
                        }

                        
    //找到所点击的Button,在其下加载子菜单
                        if (this.panel1.Controls[i].Name == ((Button)sender).Name)
                        {
                            findOutStatus 
    = true;

                            Panel panel 
    = new Panel();
                            panel.BackColor 
    = Color.AliceBlue;
                            panel.Top 
    = _ModuleButtonHeight * (i + 1);
                            panel.Width 
    = this.panel1.Width;
                            panel.Height 
    = this.panel1.Height - _ModuleButtonHeight * Module.Length;
                            
    this.panel1.Controls.Add(panel);

                            
    for (int j = 0; j < ChildModule.Length / Module.Length; j++)
                            {
                                
    if (!string.IsNullOrEmpty(ChildModule[i, j]))
                                {
                                    Button btn 
    = new Button();
                                    btn.FlatStyle 
    = FlatStyle.Flat;
                                    btn.Top 
    = _ChildButtonHeight * j;
                                    btn.Width 
    = this.panel1.Width;
                                    btn.Height 
    = _ChildButtonHeight;
                                    btn.Name 
    = string.Format("ChildButton{0}_{1}", i.ToString(), j.ToString());
                                    btn.Text 
    = ChildModule[i, j];
                                    btn.Click 
    += new EventHandler(btnChild_Click);
                                    panel.Controls.Add(btn);
                                }
                            }
                        }
                    }
                }
            }

    点击第一层菜单项,就根据点击的Button相应调整各个Button的位置,并在其下填充一个pannel控件,在这个pannel控件里面填充子菜单项.

    当填充完成的时候,就实现了类似QQ面板的功能了.在这个Click事件里面更可以加上声音效果,或者对Button和Form贴一些图片.就更像QQ面板.

    当点击子菜单,则会触发相应事件:

            private void btnChild_Click(object sender, EventArgs e)
            {
                MessageBox.Show(
    string.Format("你点击了 \"{0}\" 按钮!", ((Button)sender).Name), "系统提示", MessageBoxButtons.OK, MessageBoxIcon.Information);
            }

    完整源代码下载: https://files.cnblogs.com/KenBlove/QQPanel.7z

    (本代码修改自网络上相关代码)

  • 相关阅读:
    Python程序中的线程操作-concurrent模块
    python程序中的进程操作-进程间的数据共享
    有几个消费者就需要发送几次结束信号
    python进程池
    Python程序中的线程操作-concurrent模块
    Python程序中的线程操作-线程队列
    Python程序中的线程操作-守护线程
    进程操作-进程池
    进程池版socket并发聊天
    使用多进程请求多个url来减少网络等待浪费的时间
  • 原文地址:https://www.cnblogs.com/KenBlove/p/1300938.html
Copyright © 2011-2022 走看看