Embedding Windows Forms Controls In WPF Applications
You've seen that WPF can host Win32 controls by wrapping any HWND inside an HwndHost. And Windows Forms controls can easily be exposed as Win32 controls. (Unlike WPF controls, they are all HWND-based, so System.Windows.Forms.Control directly defines a Handle property exposing the HWND.) Therefore, you could imagine using the same techniques previously discussed to host Windows Forms controls inside WPF.
However, there is the opportunity for much richer integration between Windows Forms and WPF, without delving into the underlying HWND-based plumbing. Sure, they have different rendering engines and different controls. But they both have rich .NET-based object models with similar properties and events, and both have services (such as layout and data binding) that go above and beyond their Win32 common denominator.
Indeed, WPF takes advantage of this opportunity and also has built-in functionality for direct interoperability with Windows Forms. This support is still built on top of the Win32 HWND interoperability described in the last two sections, but with many features to make the integration much simpler. The hard work is done for you, so you can communicate more directly between the technologies, usually without the need to write any unmanaged code.
As with Win32 interoperability, WPF defines a pair of classes to cover both directions of communication. The analog to HwndHost is called WindowsFormsHost, and appears in the System.Windows.Forms.Integration namespace (in the WindowsFormsIntegration.dll assembly).
Embedding a PropertyGrid with Procedural Code
Windows Forms has several interesting built-in controls that WPF lacks in its first version. One control--the powerful PropertyGrid--helps to highlight the deep integration between Windows Forms and WPF, so let's use that inside a WPF Window. (Of course, you can also create custom Windows Forms controls and embed them in WPF Windows as well.)
The first step is to add a reference to System.Windows.Forms.dll and WindowsFormsIntegration.dll to your WPF-based project. After you've done this, your Window's Loaded event is an appropriate place to create and attach a hosted Windows Forms control. For example, let's take a simple Window containing a Grid called grid:
<Window x:Class=.Window1" xmlns=://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x=://schemas.microsoft.com/winfx/2006/xaml" Title=a Windows Forms Property Grid in WPF" Loaded=_Loaded"> private void Window_Loaded(object sender, RoutedEventArgs e) { // Create the host and the PropertyGrid control System.Windows.Forms.Integration.WindowsFormsHost host = new System.Windows.Forms.Integration.WindowsFormsHost(); System.Windows.Forms.PropertyGrid propertyGrid = new System.Windows.Forms.PropertyGrid(); // Add the PropertyGrid to the host, and the host to the WPF Grid host.Child = propertyGrid; grid.Children.Add(host); // Set a PropertyGrid-specific property propertyGrid.SelectedObject = this; }
The integration-specific code is as simple as instantiating WindowsFormsHost and setting its Child property to the desired object. WindowsFormsHost's Child property can be set to any object that derives from System.Windows.Forms.Control.
The last line, which sets PropertyGrid's SelectedObject property to the instance of the current WPF Window, enables a pretty amazing scenario. PropertyGrid displays the properties of any .NET object, and, in some cases, enables the editing of the object's values. It does this via .NET reflection. Because WPF objects are .NET objects, PropertyGrid provides a fairly rich way to edit the current Window's properties on-the-fly without writing any extra code. Figure 7 shows the previously defined Window in action. When running this application, you can see values change as you resize the Window, you can type in new property values to resize the Window, you can change its background color or border style, and so on. (The WindowsFormsHost class actually derives from HwndHost, so it supports the same HWND interoperability features described earlier, just in case you want to dig into lower-level mechanics, such as overriding its WndProc method.)

Notice that the enumeration values for properties such as HorizontalContent Alignment are automatically populated in a drop-down list, thanks to the standard treatment of .NET enums. But Figure 7 highlights some additional similarities between Windows Forms and WPF, other than being .NET-based. Notice that Window's properties are grouped into categories such as "Behavior," "Content," and "Layout." This comes from CategoryAttribute markings that are used both by Windows Forms and WPF. The type converters used by WPF are also compatible with Windows Forms, so you can type in "red" as a color, for example, and it gets automatically converted to the hexadecimal ARGB representation (#FFFF0000). Another neat thing about the PropertyGrid used in this manner is that you can see attached properties that could be applied to the object, with the syntax you would expect.