Search code examples
c#wpfwinformsformclosing

How to get an instance of hosting WinForm from a WPF user control?


I have a WPF UserControl which is being hosted either in a WPF window or in a Windows Forms Form. When the user presses the "X" button to close the hosting window/form, I want to grab this closing event and do some operations.

For this purpose I have subscribed to the loading event of the UserControl to grab the hosting windows/form instance and subscribe to its closing event.

It is working fine with an WPF window, but when I try to do the same with a Form, I get an error and I am unable to proceed.

WPFUsercontrol.xaml.cs

private void WpfUsercontrol_OnLoaded(object sender, RoutedEventArgs e)
{
    Window window = Window.GetWindow(this);
    if (window != null)
        window.Closing += window_closing;

    Form form = this.Parent as Form;    
    //Error: Cannot convert from System.Windows.DependencyObject to System.Windows.Forms.Form    
}

How can I achieve the same functionality of closing a Form as I am doing with a WPF Window?


Solution

  • You cannot just cast the WPF UserControl's parent to a System.Windows.Forms.Form even when that control is hosted in a Windows Forms Form, because hosting is not that trivial and requires additional "black magic".

    Instead, you have to get a HwndSource first and get its ElementHost instance. Having that, you can access the TopLevelControl which will be a Form you're looking for.

    var hwndSource = (HwndSource)PresentationSource.FromDependencyObject(this);
    var host = (ElementHost)Control.FromChildHandle(hwndSource.Handle);
    Form form = (Form)host.TopLevelControl;