在.NET中,我们使用try-catch-finally来处理异常。但,当一个Exception抛出,抛出Exception的代码又没有被try包围时,程序就崩溃了。

这些异常往往是你没有注意到的。在WPF中,提供了一种处理这些个异常的方式。

举例来说明。

1.先抛出个异常,不用try包围它。

在MainWindow上添加一个如下的Button。

<Window x:Class="HandlingAnUnhandledException.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="MainWindow" Height="350" Width="525">
<StackPanel>
<Button Click="OnClick">
<Button.Template>
<ControlTemplate>
<Grid>
<Ellipse Height="100" Width="250" Fill="Pink"/>
<TextBlock Text="Button to Throw Exception by DebugLZQ" VerticalAlignment="Center" HorizontalAlignment="Center"/>
</Grid>
</ControlTemplate>
</Button.Template>
</Button>
</StackPanel>
</Window>

在Button的Click事件中抛出个异常

        private void OnClick(object sender, RoutedEventArgs e)
{
throw new InvalidOperationException("Something has gone wrong.");
}

如果,我们Ctrl+F5运行这个程序,点击按钮,程序就崩溃了。
WPF如何解决这个问题呢?

2.WPF处理这种异常的方法

在App.xaml.cs中订阅DispatcherUnhandledException事件,并添加相应的事件处理。

App.xaml.cs如下:

    public partial class App : Application
{
public App()
{
DispatcherUnhandledException += App_DispatcherUnhandledException;
} void App_DispatcherUnhandledException(object sender, System.Windows.Threading.DispatcherUnhandledExceptionEventArgs e)
{
MessageBox.Show("Error encountered! Please contact support."+ Environment.NewLine + e.Exception.Message);
//Shutdown(1);
e.Handled = true;
}
}

这时,当我们Ctrl+F5运行程序。

这样,异常就被捕获并处理了,程序没有崩溃。

Update:刚百度了一下:WinForm也有类似的机制,请参考Kevin Gao的这篇博文:C# winform 捕获全局异常.

 Update

  所有 WPF 应用程序启动时都会加载两个重要的线程:一个用于呈现用户界面,另一个用于管理用户界面。呈现线程是一个在后台运行的隐藏线程,因此我们通常面对的唯一线程就是 UI 线程。

  这种方法只能捕捉UI线程的异常,及使用了Dispatcher进行线程关联了的线程(其实Dispatcher.Invoke/BeginInvoke就是将要执行的代码,扔到UI线程去执行)的异常。不能捕捉普通的子线程异常。

如:

private void OnClick(object sender, RoutedEventArgs e)
{
Dispatcher.BeginInvoke(new Action(() => { throw new InvalidOperationException("Something has gone wrong."); }));
}

也可以正常捕获。

而:

private void OnClick(object sender, RoutedEventArgs e)
{
Thread t = new Thread(() => { throw new InvalidOperationException("Something has gone wrong."); });
t.IsBackground = true;
t.Start();
}

则不能捕获。

感谢veboys博友的指点~

------------------------------------------

同样的,即使我们用一个try-catch包围如下的异常,异常也不会被Handle:

try
{
var thread = new Thread(() => {throw new Exception(); });
thread.Start();
}
catch (Exception)
{
MessageBox.Show("Will not execute!");
throw;
}
try
{
Task.Run(() =>{throw new Exception(); });
}
catch (Exception)
{
MessageBox.Show("Will not execute!");
}

--------------

对应Async await 异常:

private async void ButtonBase_OnClick(object sender, RoutedEventArgs e)
{
try
{
await Task.Run(() => { throw new Exception(); });
}
catch (Exception)
{
MessageBox.Show("Will execute!");
}
}

处理Unhandled exception异常 如下:TaskScheduler.UnobservedTaskException

    public partial class App : Application
{
protected override void OnStartup(StartupEventArgs e)
{
RegisterEvents();
base.OnStartup(e);
} private void RegisterEvents()
{
TaskScheduler.UnobservedTaskException += (sender, args) =>
{
MessageBox.Show(args.Exception.Message);
args.SetObserved();
}; AppDomain.CurrentDomain.UnhandledException += (sender, args) => MessageBox.Show("Unhandled exception.");
}
}

 Update

WPF程序的异常捕获总结

WPF整理-处理没有注意到的异常的更多相关文章

  1. WPF整理-Style

    "Consistency in a user interface is an important trait; there are many facets of consistency,   ...

  2. WPF整理-使用用户选择主题的颜色和字体

    “Sometimes it's useful to use one of the selected colors or fonts the user has chosen in theWindows ...

  3. WPF整理-自定义一个扩展标记(custom markup extension)

    "Markup extensions are used to extend the capabilities of XAML, by providing declarativeoperati ...

  4. WPF整理-XAML访问静态属性

    "XAML provides an easy way to set values of properties—type converters and the extended propert ...

  5. WPF整理-XAML构建后台类对象

    1.XAML 接触WPF的第一眼就是XAML---XAML是用来描绘界面的.其实不然! "Actually, XAML has nothing to do with UI. It's mer ...

  6. 捕捉WPF应用程序中XAML代码解析异常

    原文:捕捉WPF应用程序中XAML代码解析异常 由于WPF应用程序中XAML代码在很多时候是运行时加载处理的.比如DynamicResource,但是在编译或者运行的过程中,编写的XAML代码很可能有 ...

  7. 干!一张图整理了 Python 所有内置异常

    在编写程序时,可能会经常报出一些异常,很大一方面原因是自己的疏忽大意导致程序给出错误信息,另一方面是因为有些异常是程序运行时不可避免的,比如在爬虫时可能有几个网页的结构不一致,这时两种结构的网页用同一 ...

  8. 太干了!一张图整理了 Python 所有内置异常

    在编写程序时,可能会经常报出一些异常,很大一方面原因是自己的疏忽大意导致程序给出错误信息,另一方面是因为有些异常是程序运行时不可避免的,比如在爬虫时可能有几个网页的结构不一致,这时两种结构的网页用同一 ...

  9. WPF整理-Mutex确保Application单例运行

    有时我们不希望我们的WPF应用程序可以同时运行有多个实例,当我们试图运行第二个实例的时候,已经运行的实例也应该弹出来. 我们可以用Mutex来实现 打开App.xaml.cs,在App类中添加如下内容 ...

随机推荐

  1. Hitachi Content Platform学习

    相关资料:https://community.hds.com/groups/developer-network-for-hitachi-content-platform/content?filterI ...

  2. rman恢复报ORA-27039

    查看资源限制: AIX修改参数文件/etc/security/limits 如下: 重新su到用户下即可生效

  3. Intel.parallel.studio.xe.2015.Update.2.ISO-TBE 下载

    磁力链下载点我 还有linux版本 Intel.parallel.studio.xe.2015.Update.1.LINUX.ISO-TBE 收集自网络,要跨请跨原作者,谢谢.

  4. vue学习之旅

    大纲: 属性 事件 循环 指令 交互 过滤器 模板 计算属性 自定义过滤器和指令 组件(父子组件之间的通讯) 路由和多层路由以及占位槽slot等其他 vue-loader和模块加载(webpack)等 ...

  5. (转)论python工厂函数与内建函数

    所谓工厂函数就是指这些内建函数都是类对象, 当你调用它们时,实际上是创建了一个类实例.   工厂函数: int(),long(),float(),complex(),bool() str(),unic ...

  6. -webkit-tap-highlight-color

    css3中有henduo 新属性,tap-highlight-color;是用于元素在移动设备IOS和adnroid上被触发点击事件时,响应的背景框的颜色. 例如在Adnroid版本的微信中,点击a标 ...

  7. 安卓开发error opening trace file: No such file or directory (2)报错原因

    error opening trace file: No such file or directory (2) 这个问题的出现是因为运行的测试机android系统版本和项目api不一致导致. 改成一样 ...

  8. 调用WCF不需要添加服务引用,使用一个WCFHelper类就可以

    效果图: 调用过程: string WCFURL = "http://localhost:100/Service1.svc"; UserRequest user = new Use ...

  9. iframe中positioin:fixed失效问题

    页面中嵌套的iframe 内的 position:fixed元素定位失效fixed正常页面 此时position:fixed是根据浏览器窗口定位的,下拉一直位于左上角:以iframe形式嵌入后 此时p ...

  10. 杨氏矩阵定义及其查找的实现C++

    先介绍一下这个数据结构的定义,Young Tableau有一个m*n的矩阵,然后有一数组 a[k], 其中 k<=m*n ,然后把a[k]中的数填入 m*n 的矩阵中,填充规则为: 1.  每一 ...