How to get a IWin32Window from a WPF Window?

Tags: ,
Add comments

When building applications that mix WPF and Winforms windows (e.g. because you are using a Winforms dialog within a WPF application) you will sometimes need a System.Windows.Forms.IWin32Window interface from an WPF System.Windows.Window. This will be useful when using the WinForms OpenFileDialog and wanting to provide a parent window to the ShowDialog() method that only accepts IWin32Window as parent.

The IWin32Window interface declares only one read-only property named Handle that must be provided by the WPF Window.

Implementing the Interface

It is very simple to just add this interface to an existing WPF Window and implementing the single property:

public partial class Window1 : Window, IWin32Window
{
   public IntPtr Handle
   {
      get
      {
         var interopHelper = new WindowInteropHelper(this);
         return interopHelper.Handle;
      }
   }
}

 

Using a wrapper class

It does not look as a very good solution to add such an interface to each and every Window in you whole application only to be able to be the parent of a dialog. So instead of implementing the interface directly you could build a wrapper class that implements this interface and use this wrapper when opening a dialog:

public class Wpf32Window : IWin32Window
{
    public IntPtr Handle { get; private set; }

    public Wpf32Window(Window wpfWindow)
    {
        Handle = new WindowInteropHelper(wpfWindow).Handle;
    }
}

Opening the dialog will now look like:

d.ShowDialog( new Wpf32Window(this) );

The grand solution to this problem

I like the wrapper solution more than implementing an interface to each and every window but I do not like the changed ShowDialog() call. It just does not look natural any more. To solve this I created an extension Method to be used with the wrapper class:

public static class CommonDialogExtensions
{
    public static DialogResult ShowDialog
                               (this CommonDialog dialog, 
                                     Window parent)
    {
        return dialog.ShowDialog(new Wpf32Window(parent));
    }
}

Now the call to open a WinForms dialog with an WPF parent looks as it should look like:

d.ShowDialog(this);

3 Responses to “How to get a IWin32Window from a WPF Window?”

  1. Ticklish Techs » Blog Archive » Isn’t one OpenFileDialog enough? Says:

    [...] You should only know about one little disadvantage when using the WinForms dialog. It only accepts WinForms as a parent window no WPF windows. To overcome this limitation please read my other article about the IWin32Window interface and how to implement / provide it in WPF at http://www.ticklishtechs.net/2009/12/22/how-to-get-a-iwin32window-from-a-wpf-window/ [...]

  2. How to get a IWin32Window from a WPF Window? | Around computing Says:

    [...] Ticklish Techs » Blog Archive » How to get a IWin32Window from a WPF Window? This entry was posted in .Net. Bookmark the permalink. ← Silverlight – WriteableBitmapEx open source library Attacher un debugger au démarrage d’un processus → LikeBe the first to like this post. [...]

  3. Benny Tordrup Says:

    What about the other way around? How can the WPF version of get a WinForms (or even better: A native Win32) window as owner? The ShowDialog method only takes a System.Windows.Window object as parameter.

Leave a Reply

WP Theme & Icons by N.Design Studio
Entries RSS Comments RSS Log in