8

我看到了一个代码示例,它创建了一个Window_Loaded()由 XAML 的“加载窗口”事件调用的方法:

<Window x:Class="TestModuleLoader.Window1"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    Title="Window1" Height="300" Width="300" Loaded="Window_Loaded">
    <Grid>
        ...
    </Grid>
</Window>

但在后面的代码中,代码在构造函数和Window_Loaded()方法中都有效:

using System.Windows;

namespace TestModuleLoader
{
    public partial class Window1 : Window
    {
        public Window1()
        {
            InitializeComponent();
        }

        private void Window_Loaded(object sender, RoutedEventArgs e)
        {
            //what advantages do I have running code here? 
        }
    }
}

这样做有什么好处吗?

是否有像 ASP.NET 中那样的“窗口加载周期”,这有助于了解,例如PreRender()PostRender()等方法?

4

2 回答 2

12

是的,WPF 控件也有类似的生命周期,就像在 ASP.NET 中一样。WPF 控件的生命周期更简单,因为它基本上由初始化、加载和卸载事件(按此顺序)组成。看:

http://msdn.microsoft.com/en-us/library/ms754221.aspx

Mike Hillberg 有一篇很好的文章,展示了初始化事件和加载事件之间的区别:

http://blogs.msdn.com/mikehillberg/archive/2006/09/19/LoadedVsInitialized.aspx

于 2009-03-16T15:58:28.367 回答
3

优秀的链接,拉齐。

Edward - 您会发现最有趣的区别是,Contructor 始终是在您的 Window/Page/UserControl 上调用的第一个方法,并且您不能指望所有 DependencyProperties 都已初始化为其最终值。此外,不建议从您的构造函数中调用任何虚拟方法。

相比之下,Loaded 事件通常在初始化过程结束时调用......也就是说 - 当 Window/Page/UserControl 已完全加载到 WPF ElementTree 中时。在加载的事件中,您可以自信地调用任何方法并修改任何 DepenencyProperty,而不会出现意外结果的风险。

一个很好的模式(我目前在我的项目中使用)是在 Loaded 事件中初始化自定义依赖项属性,如果它们在初始化期间没有被修改。对于控件,如果它们被覆盖(即通过调用代码中的属性绑定),此模式允许您避免初始化“昂贵的”属性(如 DependencyProperty,它是 ObservableCollection)。

简单的答案:如果您不确定如何安全地重载构造函数,请使用 Loaded 事件。

于 2009-03-16T16:43:27.400 回答