代码之家  ›  专栏  ›  技术社区  ›  Miral

在Windows窗体中加载与显示事件

  •  24
  • Miral  · 技术社区  · 17 年前

    Windows Forms .

    传统上,我只使用Load(或者实际上是OnLoad,因为我认为重写方法比依靠设计器将事件连接到自己身上更干净),因为这在所有版本的.NET中都可用。在.NET2.0中引入了显示的事件。

    现在,如果您查看MSDN文档中关于这些的描述(“加载:在表单首次显示之前发生。”,“显示:在表单首次显示时发生。”),您会发现

    然而,实验表明,所示事件总是发生 之前

    (我目前的解决方案是在显示表单之前和之后都执行一些操作,即对“显示之前”的内容使用OnLoad,并为“显示之后”的内容启动一个短时间的一次性计时器。它工作正常可靠,但有点难看,我希望有一个更干净的解决方案。但看起来显示的事件不是这样。)

    6 回复  |  直到 13 年前
        1
  •  63
  •   Hans Passant    14 年前

    避免使用MessageBox.Show()对此进行调试。它泵送一个消息循环,干扰正常的事件流。这个 负载 事件由Windows在窗口变为可见之前发送WM_SHOWWINDOW消息触发。“您的窗口现在已完全显示”没有窗口通知,因此WF设计师想出了一个技巧来生成 事件它们使用Control.BeginInvoke(),确保在程序再次空闲并重新进入消息循环时调用OnShown()方法。

    之前 显示窗口。

    除了MessageBox之外,还有很多其他方法可以获得诊断。Debug.Print()和Console.WriteLine()非常方便,它们的输出将被发送到 Visual Studio Output Window breakpoint 我也能创造奇迹。

        2
  •  20
  •   Community Mohan Dere    14 年前

    这是我追踪的事件顺序。这可能会帮助其他人决定如何调用或设置自定义事件处理

    表格-更改客户规模:2010年8月14日上午10:40:28
    表单-添加控件-按钮1:8/14/2010 10:40:29 AM

    创建的窗体-句柄:8/14/2010 10:40:29 AM

    表单-表单加载事件:2010年8月14日上午10:40:29

    表单-创建控件:2010年8月14日上午10:40:29
    表格-ON激活日期:2010年8月14日上午10:40:29
    表格-显示日期:2010年8月14日上午10:40:29
    表单-OnPaint:2010年8月14日上午10:40:29

    表单-OnPaint:2010年8月14日上午10:40:29

        3
  •  8
  •   DavidRR Chris Brandsma    10 年前

    这个 Shown 事件发生在 Load 事件主要区别不在于 形式上的,但在形式上的

    为了澄清,这里有一个例子。考虑具有默认大小的窗体。 100, 200 WindowState Maximized 负载 事件处理程序,大小将为 100, 200 展示 事件处理程序,大小将是您的 屏幕大小 .

        4
  •  2
  •   Miral    17 年前

    好的,我想我已经弄清楚了现在到底发生了什么,以及我的困惑是从哪里来的(尽管不是这样) 为什么? 它的行为就是这样)。看起来显示的事件实际上发生了

    鉴于此代码:

     protected override OnLoad(EventArgs e)
    {
        MessageBox.Show("Enter Load");
        base.OnLoad(e);
        MessageBox.Show("Exit Load");
    }
    
    protected override OnShown(EventArgs e)
    {
        MessageBox.Show("Enter Shown");
        base.OnShown(e);
        MessageBox.Show("Exit Shown");
    }
    

    1. 输入负载
    2. 输入显示的
    3. 出口负荷

    没有一个 在这些情况下,屏幕上实际可见的形式(已绘制)。

    出现在屏幕上 之前 此时会出现“输入显示”消息。它似乎是在它真正反对的base OnLoad调用之后执行的代码。

        5
  •  1
  •   Fredou    17 年前

    使用空项目执行快速测试:

    Public Class Form1
    
    Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
        MsgBox("load") 'form is still visible = false
    End Sub
    
    Private Sub Form1_Shown(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Shown
        MsgBox("shown") ' form is now visible = true
    End Sub
    End Class
    
        6
  •  0
  •   Cyril Gupta    17 年前

    我只是在显示之前检查并加载火。

    你的方法显然有问题。

    推荐文章