详解WPF中的APP生命周期以及全局异常捕获

 更新时间:2023年3月3日 15:46  点击:679 作者:步、步、为营

APP生命周期

wpf项目目录中有一个App.xaml.cs文件,该文件中App是一个partical类,与之对应的另一partical部分在App.g.i.cs文件中,该文件是在编译的时候WPF自动生成的。程序的入口Main方法在该文件中定义。

[System.STAThreadAttribute()]
[System.Diagnostics.DebuggerNonUserCodeAttribute()]
[System.CodeDom.Compiler.GeneratedCodeAttribute("PresentationBuildTasks", "7.0.1.0")]
public static void Main() {
    WpfApp.App app = new WpfApp.App();
    app.InitializeComponent();//初始化Xaml
    app.Run();//程序运行
}

APP类继承自Application,常见的生命周期事件有以下几个:

  • Startup:在调用 Application 对象的 Run 方法时发生
  • Navigating:在应用程序中的导航器请求新导航时发生(针对Browser类型的应用)
  • LoadCompleted:在已经加载、分析并开始呈现应用程序中的导航器导航到的内容时发生
  • Navigated:在已经找到应用程序中的导航器要导航到的内容时发生,尽管此时该内容可能尚未完成加载
  • NavigationFailed:在应用程序中的导航器在导航到所请求内容时出现错误的情况下发生
  • NavigationProgress:在由应用程序中的导航器管理的下载过程中定期发生,以提供导航进度信息
  • NavigationStopped:在调用应用程序中的导航器的 StopLoading 方法时发生,或者当导航器在当前导航正在进行期间请求了一个新导航时发生
  • SessionEnding:在用户通过注销或关闭操作系统而结束 Windows 会话时发生
  • Activated:当应用程序成为前台应用程序时发生,App任意一个窗口激活
  • Deactivated:当应用程序停止作为前台应用程序时发生,App中所有窗口非激活
  • Exit:在应用程序关闭之前发生(无法像SessionEnding事件进行取消)

对于普通窗体程序,从开始到结束会依次调用如下事件

-----App_Startup
-----App_Navigating
-----App_Activated
-----App_Exit

窗体生命周期事件

在APP运行后,会启动窗体,窗体常用的声明周期事件如下:

  • SourceInitialized:操作系统给窗口分配句柄的时候触发,注意WPF窗体里面的控件是没有句柄的
  • ContentRendered:窗体内容渲染后触发
  • Loaded:窗体布局加载完成即准备好交互后触发
  • Activated:窗体激活
  • Deactivated:窗体失去焦点
  • Closing:调用关闭窗体时触发,此时可以取消操作
  • Closed:窗体关闭后

全局异常捕获

对于异常捕获一般使用try-catch语句进行捕获,但是对于全局的异常可以在App中进行捕获。

  • DispatcherUnhandledException:在异常由应用程序引发但未进行处理时发生针对UI线程,无法捕获多线程异常
  • AppDomain.CurrentDomain.UnhandledException:专门捕获所有线程中的异常
  • TaskScheduler.UnobservedTaskException:专门捕获Task异常

案例:

APP中进行全局异常捕获

public partial class App : Application
{
    public App()
    {
        //在异常由应用程序引发但未进行处理时发生。UI线程
        //无法捕获多线程异常
        this.DispatcherUnhandledException += App_DispatcherUnhandledException;
        //专门捕获所有线程中的异常
        AppDomain.CurrentDomain.UnhandledException += CurrentDomain_UnhandledException;
        //专门捕获Task异常
        TaskScheduler.UnobservedTaskException += TaskScheduler_UnobservedTaskException;
    }
    private void App_DispatcherUnhandledException(object sender, System.Windows.Threading.DispatcherUnhandledExceptionEventArgs e)
    {
        Debug.WriteLine("-----App_DispatcherUnhandledException--UI线程" + e.Exception.Message);
    }
    private void CurrentDomain_UnhandledException(object sender, UnhandledExceptionEventArgs e)
    {
        Debug.WriteLine("-----CurrentDomain_UnhandledException--其他线程" + (e.ExceptionObject as Exception).Message);
    }
    private void TaskScheduler_UnobservedTaskException(object? sender, UnobservedTaskExceptionEventArgs e)
    {
        Debug.WriteLine("-----TaskScheduler_UnobservedTaskException--Task测试" + e.Exception.Message);
        e.SetObserved();
    }
}

窗体中抛异常

public partial class MainWindow : Window
{
    int i = 0;
    public MainWindow()
    {
        InitializeComponent();
        //1、ui线程异常测试
        _ = 1 / i;

        //2、其他线程异常测试
        new Thread(new ThreadStart(() => { _ = 1 / i; })).Start();

        //3、Task异常测试
        Task.Run(() =>
        {
            _ = 1 / i;
        });
    }   
}

异常结果说明
只打开异常1-----App_DispatcherUnhandledException--UI线程-----CurrentDomain_UnhandledException--其他线程UI线程中的异常DispatcherUnhandledException和AppDomain.CurrentDomain.UnhandledException均能捕获到
只打开异常2-----CurrentDomain_UnhandledException--其他线程只有AppDomain.CurrentDomain.UnhandledException可以捕获
只打开异常3-----TaskScheduler_UnobservedTaskException--Task测试只有TaskScheduler.UnobservedTaskException可以捕获到Task异常

备注:Task中的异常并不是立刻就能捕获到的,而是等到垃圾回收的时候进行捕获。如果想立刻进行捕获则可以调用GC.Collect(0);GC.WaitForPendingFinalizers();

到此这篇关于详解WPF中的APP生命周期以及全局异常捕获的文章就介绍到这了,更多相关WPF生命周期 全局异常捕获内容请搜索猪先飞以前的文章或继续浏览下面的相关文章希望大家以后多多支持猪先飞!

原文出处:https://www.cnblogs.com/qsnn/p/17068129.html

[!--infotagslink--]

相关文章

  • c# WPF中通过双击编辑DataGrid中Cell的示例(附源码)

    这篇文章主要介绍了c# WPF中通过双击编辑DataGrid中Cell的示例(附源码),帮助大家更好的理解和学习使用c#,感兴趣的朋友可以了解下...2021-03-03
  • Vue生命周期activated之返回上一页不重新请求数据操作

    这篇文章主要介绍了Vue生命周期activated之返回上一页不重新请求数据操作,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧...2020-07-26
  • WPF实现类似360安全卫士界面的程序源码分享

    最近在网上看到了新版的360安全卫士,感觉界面还不错,于是用WPF制作了一个,时间有限,一些具体的控件没有制作,用图片代替了。感兴趣的朋友一起跟着小编学习WPF实现类似360安全卫士界面的程序源码分享...2020-06-25
  • Python同时处理多个异常的方法

    这篇文章主要介绍了Python同时处理多个异常的方法,文中讲解非常细致,代码帮助大家更好的理解和学习,感兴趣的朋友可以了解下...2020-07-29
  • Angular处理未可知异常错误的方法详解

    这篇文章主要给大家介绍了关于Angular如何处理未可知异常错误的相关资料,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧...2021-01-17
  • java中的空指针异常情况以及解决方案

    这篇文章主要介绍了java中的空指针异常情况以及解决方案,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教...2021-10-02
  • 详解C#编程中异常的创建和引发以及异常处理

    这篇文章主要介绍了C#编程中异常的创建和引发以及异常处理,文中介绍了Catch块和Finally块等基本的异常处理要点,需要的朋友可以参考下...2020-06-25
  • Vue生命周期和钩子函数的详解与经典面试题

    Vue生命周期是指vue实例对象从创建之初到销毁的过程,vue所有功能的实现都是围绕其生命周期进行的,下面这篇文章主要给大家介绍了关于Vue生命周期和钩子函数的相关资料,需要的朋友可以参考下...2021-10-30
  • WPF仿三星手机充电界面实现代码

    这篇文章主要为大家详细介绍了WPF仿三星手机充电界面实现代码,具有一定的参考价值,感兴趣的小伙伴们可以参考一下...2020-06-25
  • C# WPF 通过委托实现多窗口间的传值的方法

    这篇文章主要介绍了C# WPF 通过委托实现多窗口间的传值的方法,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧...2020-06-25
  • React Class组件生命周期及执行顺序

    这篇文章主要介绍了React Class组件生命周期,包括react组件的两种定义方式和class组件不同阶段生命周期函数执行顺序,本文给大家介绍的非常详细,需要的朋友可以参考下...2021-08-14
  • Caused by: java.lang.ClassNotFoundException: org.apache.commons.collections.Transformer异常

    这篇文章主要介绍了Caused by: java.lang.ClassNotFoundException: org.objectweb.asm.Type异常,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧...2020-07-10
  • Spring异常捕获且回滚事务解决方案

    这篇文章主要介绍了Spring异常捕获且回滚事务解决方案,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下...2020-06-03
  • 详解Vue生命周期的示例

    本篇文章主要介绍了详解Vue生命周期的示例,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧 ...2017-03-13
  • 通过实例了解Python异常处理机制底层实现

    这篇文章主要介绍了通过实例了解Python异常处理机制底层实现,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下...2020-07-24
  • 浅谈vue生命周期共有几个阶段?分别是什么?

    这篇文章主要介绍了浅谈vue生命周期共有几个阶段?分别是什么?具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧...2020-08-07
  • 详解JavaScript错误捕获

    这篇文章主要介绍了JavaScript错误捕获的相关资料,帮助大家更好的理解和学习使用JavaScript,感兴趣的朋友可以了解下...2021-04-24
  • C#中WPF使用多线程调用窗体组件的方法

    这篇文章主要介绍了C#中WPF使用多线程调用窗体组件的方法,涉及C#中多线程的使用技巧,具有一定参考借鉴价值,需要的朋友可以参考下...2020-06-25
  • 基于事件冒泡、事件捕获和事件委托详解

    这篇文章主要介绍了事件冒泡、事件捕获和事件委托,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教...2021-07-08
  • WPF TextBox实现按字节长度限制输入功能

    这篇文章主要为大家详细介绍了WPF TextBox实现按字节长度限制输入功能,具有一定的参考价值,感兴趣的小伙伴们可以参考一下...2020-06-25