技术开发 频道

WinForm应用框架:动态创建业务窗体

  业务窗体的基类

  所有的业务窗体都继承自这个基类BaseForm

WinForm应用框架设计:业务窗体的基类

  这个窗体基类有三个公开的属性

        /// <summary>
        
/// 菜单数据
        
/// </summary>
        public MenuModel FormMenu { get; set; }
        
/// <summary>
        
/// tab按钮
        
/// </summary>
        public TabBTN FormTabBTN { get; set; }
        
/// <summary>
        
/// 子菜单
        
/// </summary>
        public Label SubMenu { get; set; }

  这三个属性在后面会用到,这里先不说了

        /// <summary>
        
/// 构造函数
        
/// </summary>
        public BaseForm()
        {
            InitializeComponent();
            
this.TopLevel = false;
        }

  一般顶层窗体是不允许被当作子控件放在容器控件中的,所以我们要设置窗体的TopLevel属性

        /// <summary>
        
/// tab按钮选中事件;
        
/// </summary>
        
/// <param name="sender"></param>
        
/// <param name="e"></param>
        public virtual void tbn_OnSelect(object sender, EventArgs e)
        {
            
this.Show();
        }
        
/// <summary>
        
/// tab按钮关闭事件
        
/// </summary>
        
/// <param name="sender"></param>
        
/// <param name="e"></param>
        public virtual void tbn_OnClose(object sender, EventArgs e)
        {
            
this.Close();
        }

  这是tab按钮的两个事件,是在创建tab按钮的时候注册的

       待会我们再说怎么创建的tab按钮和注册这两个事件~

  因为并不是在baseForm里创建的tab按钮

       private void BaseForm_VisibleChanged(object sender, EventArgs e)
        {
            
if (Utils.IsInDesignMode())
            {
                
return;
            }
            
this.VisibleChanged -= new EventHandler(BaseForm_VisibleChanged);
            var mf
= Utils.GetMainForm();
            
if (this.Visible)
            {
                
foreach (var hf in mf.FormHistory)
                {
                    
if (hf.FormMenu.Url.Equals(this.FormMenu.Url))
                    {
                        
continue;
                    }
                    
if (hf.Visible)
                    {
                        hf.Hide();
                    }
                }
                FormTabBTN.SelectMe();
                mf.FormHistory.Remove(
this);
                mf.FormHistory.Insert(
0, this);
                mf.MainContainerP.Controls.Clear();
                mf.MainContainerP.Controls.Add(
this);
                SubMenu.BackColor
= SystemColors.Info;
                
//TODO:系统名称可以做到数据库里去
                mf.Text = string.Format("XXX管理系统-{0}", FormMenu.MenuName);
            }
            
else
            {                
                FormTabBTN.DisSelectMe();
                SubMenu.BackColor
= Color.Transparent;
            }
            
this.VisibleChanged += new EventHandler(BaseForm_VisibleChanged);
        }

  这是BaseForm的一个重要事件

  隐藏和显示切换的时候被触发

  如果从隐藏变为显示

先遍历所有打开过的业务窗体,如果有是显示状态的,那么就把他隐藏掉,因为当前系统只能有一个业务窗体是出于显示状态的
接着选中TAB按钮,
FormHistory的Remove和Insert主要是为了让系统记住哪些窗体是最近显示过的;
MainContainerP的Clear和Add是为了让窗体显示在容器控件内

  如果从显示变为隐藏

TAB按钮取消选中,
子菜单的背景颜色变成透明的,(其实就是子菜单取消选中)

  事件处理的开始取消了事件注册,事件处理的结束有把事件注册进去了,这样做主要是为了避免多次触发事件

  Utils.GetMainForm();获取主窗口的代码如下:

        /// <summary>
        
/// 主窗口
        
/// </summary>
        private static MainForm mf;
        
/// <summary>
        
/// 获取主窗口
        
/// </summary>
        
/// <returns></returns>
        public static MainForm GetMainForm()
        {
            
if (mf == null)
            {
                mf
= Application.OpenForms["MainForm"] as MainForm;
            }
            
return mf;
        }

  当业务窗体关闭时要处理一些逻辑,代码如下:

       private void BaseForm_FormClosing(object sender, FormClosingEventArgs e)
        {
            
this.VisibleChanged -= new EventHandler(BaseForm_VisibleChanged);
            var mf
= Utils.GetMainForm();
            mf.FormHistory.Remove(
this);
            
this.SubMenu.BackColor = Color.Transparent;
            
if (mf.FormHistory.Count > 0)
            {
                mf.FormHistory[
0].Show();
            }
            
foreach (var f in mf.FormHistory)
            {
                
if (f.FormTabBTN.Left > FormTabBTN.Left)
                {
                    f.FormTabBTN.Left
-= (FormTabBTN.Width + 6);
                }
            }
            mf.TabContainerP.Controls.Remove(FormTabBTN);
        }

  取消事件注册

  移除历史记录

  取消子菜单选中

  打开最近一次打开的业务窗体(如果有的话)

  重写设置tab按钮的位置(主要是被关闭的tab按钮的右边的tab按钮)

  删除tab按钮

0