Microsoft KB Archive/197503

= PRB: Focus Problem Using MFC Control on MDI Child Form =

Article ID: 197503

Article Last Modified on 5/12/2003

-

APPLIES TO


 * Microsoft Visual Basic 5.0 Learning Edition
 * Microsoft Visual Basic 6.0 Learning Edition
 * Microsoft Visual Basic 5.0 Professional Edition
 * Microsoft Visual Basic 6.0 Professional Edition
 * Microsoft Visual Basic 5.0 Enterprise Edition
 * Microsoft Visual Basic 6.0 Enterprise Edition

-



This article was previously published under Q197503



SYMPTOMS
You put controls created in Visual C++ using the Microsoft Foundation Classes (MFC) on a multiple-document interface (MDI) child form. Additionally, you have some non-MFC controls on the MDI form (parent). You find that after you click the MFC control on the child form, click one of the non-MFC controls on the MDI form and then press the tab key, the focus moves to another control on the child form instead of the MDI form.

This behavior also occurs in similar situations where the project consists of child and parent forms with MFC controls used on at least one of the forms.



CAUSE
When you click the MFC control, the control is UIActivated in the container. However, when you click another non-MFC control on another form, the container does not UIDeactivate the MFC control automatically.



RESOLUTION
To resolve the problem, UIDeactivate the control when it loses the focus.



STATUS
This behavior is by design.



Steps to Create a MFC Control

 * 1) In Visual C, from the File menu, choose "New...", click the Projects tab and then select "MFC ActiveX Control Wizard".
 * 2) In the Project name text box, type MyMfcCtrl, and then click OK. Keep all the default settings as you go through the wizard steps.
 * 3) Build the project and the control registers automatically.

Steps to Create a Visual Basic Sample
 From the File menu, choose New Project then select the "VB Application Wizard". Click OK and keep all the default settings as you go through the wizard steps. From the Project menu, choose "Components..." then select "MyMfcCtrl ActiveX control module". Click OK. Add a PictureBox to frmMain. Add two Command buttons and then one MyMfcCtrl to the PictureBox and keep the default settings. Remove the RichTextBox on the frmDocument. Add a text box and then a MyMfcCtrl to frmDocument and keep the default names.</li> Remove all of the code in the code window of frmDocument.</li> Press F5 to run the application, then follow these steps:

<ol style="list-style-type: lower-alpha;"> Click a text box on the child form.</li> Click the Command1 button on the MDI form.</li> Press the TAB key.

The focus is now on the Command2 button on the MDI form, which is correct.</li> Click the MFC control on the child form.</li> Click the MFC control on the MDI form.</li> Press the TAB key twice (first TAB moves focus to the PictureBox.)

The focus is now on the Command1 button on the MDI form, which is correct.</li> Click the MFC control on the child form.</li> Click the Command1 button on the MDI form.</li> Press the TAB key.

The focus is now on the text box on the child form. This is incorrect.</li> Close the project.</li></ol> </li></ol>

Steps to Resolve the Problem (Modify the OCX)
<ol> Open the MyMfcCtrl project created in the "Steps to Create a MFC Control" section.</li>  From the View menu, select Class Wizard then click the Message Maps tab. Choose CMyMfcCtrlCtrl from the Class Name drop-down list box. Double- click the WM_SETFOCUS item in the Messages list box. Click OK and the following message handler is added by the wizard: void CMyMfcCtrlCtrl::OnSetFocus(CWnd* pOldWnd)

</li>  Modify the OnSetFocus message handler in the MyMfcCtrlCtl.cpp file to be as follows: void CMyMfcCtrlCtrl::OnSetFocus(CWnd* pOldWnd) {        COleControl::OnSetFocus(pOldWnd); // this will make sure that the control will be activated in place OnActivateInPlace(TRUE, NULL); }                       </li>  In ClassView, right-click _DMyMfcCtrl then select "Add Method...". In the Add Method dialog box, type DeActivate in the External name drop-down list box. Select void from the Return Type drop-down list box. Click OK and the new automation method DeActivate is added. Change this function in the MyMfcCtrlCtl.cpp file as follows: void CMyMfcCtrlCtrl::DeActivate {        // TODO: Add your dispatch handler code here m_xOleInPlaceObject.UIDeactivate; }                       </li> <li>Build the project again.</li></ol>

Steps to Resolve the Problem (Modify Visual Basic)
<ol> <li> Open the Visual Basic project created previously and add the following code into the Code window of the child form: Private Sub MyMfcCtrl1_LostFocus MyMfcCtrl1.DeActivate End Sub </li> <li>Test the Visual Basic project again. Now, it works correctly.</li></ol>

<div class="references_section">