正确隐藏所有者表单 [英] Properly Hiding Owner Form

查看:26
本文介绍了正确隐藏所有者表单的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

以下代码在子窗体打开时隐藏父窗体 (Owner).这段代码是否正确处理了应用程序(短暂地没有可见窗口)可能在转换中失去焦点的问题?

The following code hides the parent (Owner) form while the child form is open. Does this code properly handle the issue where the application (briefly with no visible windows) may lose focus in the transition?

部分主表单

using System;
using System.Windows.Forms;

namespace multiForms
{
    public partial class mainFrm : Form
    {
        public mainFrm()
        {
            InitializeComponent();

            this.button1.Click += new System.EventHandler(this.button1_Click);
        }

        private void button1_Click(object sender, EventArgs e)
        {
            childFrm subForm = new childFrm();
            subForm.ShowDialog(this);
            subForm.Dispose();
        }

    }
}

部分子表单:

using System;
using System.Windows.Forms;

namespace multiForms
{
    public partial class childFrm : Form
    {
        public childFrm()
        {
            InitializeComponent();

            this.Shown += new System.EventHandler(this.childFrm_Shown);
            this.FormClosing += new System.Windows.Forms.FormClosingEventHandler(this.childFrm_FormClosing);
        }

        private void childFrm_Shown(object sender, EventArgs e)
        {
            this.Owner.Hide();
        }

        private void childFrm_FormClosing(object sender, FormClosingEventArgs e)
        {
            this.Owner.Show();
        }

    }
}

推荐答案

它会正常工作.

然而,这在技术上并不正确.FormClosing 事件可以取消,它可能无法完全由您控制,因为任何代码都可以为该事件编写事件处理程序并将 e.Cancel 属性设置为 true.在这种情况下,停止依赖事件变得很重要.弹性代码会覆盖触发事件的方法.对于每个 Xxxx 事件,都有一个相应的虚拟 OnXxxx() 方法可以覆盖.

It is not technically correct however. The FormClosing event can be cancelled, it may not be completely under your control since any code can write an event handler for the event and set the e.Cancel property to true. In circumstances like this it gets to be important to stop relying on events. Resilient code overrides the method that fires the event instead. For every Xxxx event there's a corresponding virtual OnXxxx() method that you can override.

在这种情况下,这样的方法覆盖应该是这样的:

In this case, such a method override should like this:

    protected override void OnFormClosing(FormClosingEventArgs e) {
        base.OnFormClosing(e);
        if (!e.Cancel && this.Owner != null) this.Owner.Show();
    }

现在一切正常.如果周围有任何代码订阅 FormClosing 并取消它,那么您将不会显示所有者.

Now it works fine. If there is any code around that subscribes FormClosing and cancels it then you won't show the owner.

请注意覆盖如何为您提供三种不同的选择:

Do note how the override gives you a choice of three different things you can do:

  • 您可以先调用 base.OnXxxx(),这样您就可以控制了.
  • 您进行修改,然后调用 base.OnXxxx(),让其他代码处于控制之中.通常是正确的选择,只是不是在这种特定情况下.但是,如果您例如显示常见的是否要保存更改"消息框,则使用什么.它应该在您触发事件之前显示,如果用户点击取消,那么您根本不想触发该事件.
  • 您可能根本不调用 base.OnXxxx(),只有在您高度自定义事件处理并且允许事件仍然触发可能会破坏程序时才这样做.非常罕见.

请注意编写这样的事件处理代码的感觉良好"因素.一个类监听它的自己 事件并没有多大意义.事件用于外部代码.就像所有者中的代码一样,这确实属于.它恰好在 Winforms 编程中很常见,因为设计器可以轻松添加事件处理程序,并且它与 VB6 事件模型相匹配,而 Winforms 旨在取代该编程工具.编写 OnXxxx() 方法重写还是很容易的,IntelliSense 支持得很好.只需键入protected override on"并从那里自动完成.这是正确的 OOPy 方式.

Do note the "feels good" factor of writing event handling code like this. A class listening to its own events doesn't make much sense. Events are meant for external code. Like the code in the Owner, where this really belongs. It just happens to be common in Winforms programming because the designer makes it easy to add event handlers and it matches the VB6 eventing model, the programming tool that Winforms was meant to replace. It is still very easy to write the OnXxxx() method override, IntelliSense supports it well. Just type "protected override on" and auto-complete from there. It is the correct OOPy way.

这篇关于正确隐藏所有者表单的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆