Although Microsoft Foundation Classes (MFC) admittedly are not the future of rich client development frameworks, many companies have a huge investment in the technology and Microsoft continues to support MFC to ensure that it works well with Windows Forms today and Avalon in the future. The migration path from MFC to fully native applications is a slow one. Windows Forms lacks many of the advanced features of MFC, such as an in-built Document/View Framework and Windows shell integration, which prevents full migration for applications that rely on these features. Even if full framework feature parity existed, porting and testing an application from one framework to another is a massive job. For these reasons, having bridging technologies between the past (MFC) and the future (Windows Forms and Avalon) is very important.
This first of two articles looks at MFC today, and shows how much easier MFC 8.0 makes Windows Forms integration. Part II will drill into the MFC classes that implement the integration, as well as offer a brief look ahead at integrating with Avalon.
The Evolution of MFC
Before diving into Windows Forms/MFC integration, let's look at the evolution of MFC. In the beginning, a C++ developer had no application frameworks for writing Windows applications. He or she started building an application typically by copying and pasting an existing code base that contained skeleton code like message pumps that a Windows application required in order to get up and running.
This cut-and-paste approach had obvious problems, so Microsoft released a C++ framework called the Microsoft Foundation Classes that made getting a Windows application up and running relatively easy. As with Visual Basic, MFC contained wrappers for the underlying Windows controls that made interacting with the control pretty easy. The vast differences between the Visual Basic Forms library and MFC resulted in very little similarity between a Visual Basic control and a MFC control.
The differences between VB and MFC controls became an issue for third-party control vendors. Because a third-party Visual Basic control (VBX) was very different from a third-party MFC control, a vendor either needed two controls that provided the same UI functionality but were implemented very differently, or it ignored one of the markets. The VB market turned out to be much bigger and more successful, and VBX controls formed the basis for ActiveX (OCX) controls in the 32-bit world. Visual C++ was a great OCX producer, and it had the modern, lightweight Active Template Library (ATL) to produce COM-based DLLs and ActiveX controls. Ironically enough, Visual C++ and MFC were not great OCX consumers compared with Visual Basic.
The situation got even weirder with .NET. The new .NET Windows Forms totally superseded the Visual Basic Forms library. MFC and ATL continued to ship and receive support from Microsoft, and Visual C++ also gained the ability to write Windows Forms applications, though the initial release of Visual Studio.NET did not include a WYSIWYG designer. Windows Forms controls replaced OCXs as the favored delivery format for third-party control vendors, which meant that the vast majority of Visual C++ applications—which were not based on the managed Windows Forms framework—were again locked out of the most recent control delivery format (so it was back to the VBX days in some ways).
Thankfully, the situation improves with MFC 8.0. It contains a bunch of new classes that allow Windows Forms controls to be hosted within MFC Views and MFC Dialogs. This article doesn't drill into the various classes and technologies that are used to achieve this integration (Part II will), but it instead looks at how simple using the integration is.
Integrating MFC Applications and Windows Forms Controls
The well-traveled Scribble sample application that shipped with Visual C++ 6 can demonstrate how easy it is to integrate a Windows Forms control with an MFC application written well before the advent of managed code. To dispel any doubts that this technology works well with simple dummy controls but falls apart when you use real-world controls, this demonstration uses a free third-party control that is specialized for the input of numeric and currency data to replace Scribble's existing pen width thickness text box control. This new control prevents non-numeric text from being typed into a text box. You can download this control from WindowsForms.net.
The first step in the integration is to upgrade Scribble to the new version of the Visual Studio file format. Simply open the DSW file that contains the project workspace with Visual C++ 2005 and agree to the upgrade prompt. You then can run Scribble without any code modifications, though there will be a couple of minor warnings. The next step is to switch from native to managed compilation, which you can do on the General page of the Configuration Properties for the solution, as shown in Figure 1.
Figure 1: Configuring a C++ Application for Managed Compilation