From 3cbcb3375b8762cf046289925e5e458c9ef717ca Mon Sep 17 00:00:00 2001 From: Siegfried Pammer <siegfriedpammer@gmail.com> Date: Tue, 30 Aug 2011 18:57:07 +0200 Subject: [PATCH] fix exception on designer unload --- .../FormsDesignerViewContent.cs | 59 +++++++++---------- 1 file changed, 29 insertions(+), 30 deletions(-) diff --git a/src/AddIns/DisplayBindings/FormsDesigner/FormsDesigner.AddIn/FormsDesignerViewContent.cs b/src/AddIns/DisplayBindings/FormsDesigner/FormsDesigner.AddIn/FormsDesignerViewContent.cs index dc9f71b9f4..403f09d40e 100644 --- a/src/AddIns/DisplayBindings/FormsDesigner/FormsDesigner.AddIn/FormsDesignerViewContent.cs +++ b/src/AddIns/DisplayBindings/FormsDesigner/FormsDesigner.AddIn/FormsDesignerViewContent.cs @@ -479,37 +479,38 @@ namespace ICSharpCode.FormsDesigner appDomainHost.SelectionChanged -= new EventHandlerProxy(SelectionChangedHandler); - appDomainHost.DesignSurfaceUnloaded += delegate { - ServiceContainer serviceContainer = appDomainHost.GetService(typeof(ServiceContainer)) as ServiceContainer; - if (serviceContainer != null) { - // Workaround for .NET bug: .NET unregisters the designer host only if no component throws an exception, - // but then in a finally block assumes that the designer host is already unloaded. - // Thus we would get the confusing "InvalidOperationException: The container cannot be disposed at design time" - // when any component throws an exception. - - // See http://community.sharpdevelop.net/forums/p/10928/35288.aspx - // Reproducible with a custom control that has a designer that crashes on unloading - // e.g. http://www.codeproject.com/KB/toolbars/WinFormsRibbon.aspx - - // We work around this problem by unregistering the designer host manually. - try { - var services = (Dictionary<Type, object>)typeof(ServiceContainer).InvokeMember( - "Services", - BindingFlags.Instance | BindingFlags.GetProperty | BindingFlags.NonPublic, - null, serviceContainer, null); - foreach (var pair in services.ToArray()) { - if (pair.Value is IDesignerHost) { - serviceContainer.GetType().InvokeMember( - "RemoveFixedService", - BindingFlags.Instance | BindingFlags.InvokeMethod | BindingFlags.NonPublic, - null, serviceContainer, new object[] { pair.Key }); + appDomainHost.DesignSurfaceUnloaded += new EventHandlerProxy( + delegate { + ServiceContainer serviceContainer = appDomainHost.GetService(typeof(ServiceContainer)) as ServiceContainer; + if (serviceContainer != null) { + // Workaround for .NET bug: .NET unregisters the designer host only if no component throws an exception, + // but then in a finally block assumes that the designer host is already unloaded. + // Thus we would get the confusing "InvalidOperationException: The container cannot be disposed at design time" + // when any component throws an exception. + + // See http://community.sharpdevelop.net/forums/p/10928/35288.aspx + // Reproducible with a custom control that has a designer that crashes on unloading + // e.g. http://www.codeproject.com/KB/toolbars/WinFormsRibbon.aspx + + // We work around this problem by unregistering the designer host manually. + try { + var services = (Dictionary<Type, object>)typeof(ServiceContainer).InvokeMember( + "Services", + BindingFlags.Instance | BindingFlags.GetProperty | BindingFlags.NonPublic, + null, serviceContainer, null); + foreach (var pair in services.ToArray()) { + if (pair.Value is IDesignerHost) { + serviceContainer.GetType().InvokeMember( + "RemoveFixedService", + BindingFlags.Instance | BindingFlags.InvokeMethod | BindingFlags.NonPublic, + null, serviceContainer, new object[] { pair.Key }); + } } + } catch (Exception ex) { + LoggingService.Error(ex); } - } catch (Exception ex) { - LoggingService.Error(ex); } - } - }; + }); try { appDomainHost.DisposeDesignSurface(); } catch (ExceptionCollection exceptions) { @@ -600,8 +601,6 @@ namespace ICSharpCode.FormsDesigner // This is required on Vista, I don't know why it works correctly in XP CustomWindowsFormsHost designView = WrapInCustomHost(appDomainHost.DesignSurfaceView, enableFontInheritance: false); - - this.UserContent = designView; LoggingService.Debug("FormsDesigner loaded, setting ActiveDesignSurface to " + appDomainHost.DesignSurfaceName); appDomainHost.ActivateDesignSurface();