I am making a doc/view arch SDI application.
I invoke a COptionsDialog in CSquaresView.
void CSquaresView::OnOptions()
{
COptionsDialog dlg(this);
if (dlg.DoModal() == IDOK)
...
}
In COptionsDialog I want to access CSquaresView.
BOOL COptionsDialog::OnInitDialog()
{
CDialog::OnInitDialog();
CWnd *pParent = GetParent();
if (pParent) {
CSquaresView *pView = dynamic_cast<CSquaresView*>(pParent); //pView is always NULL
if (pView != NULL)
{
CSquaresDoc* pDoc = pView->GetDocument();
...
}
But I always get pView as NULL;
Please help me to solve this problem.
The observed behavior makes sense. A (modal) dialog's owner must be
CView-derived class instances generally are child windows. As such they cannot be the owner of a (modal) dialog. When you pass a child window into the c'tor of aCDialog-derived class, the system walks up the window hierarchy until it finds an overlapped or pop-up window, and uses that as the owner of the dialog. Regardless of whether you then callGetParent,GetAncestor, orCWnd::GetOwner, it is this true owner (usually yourCFrameWnd-derived implementation) where window traversal starts.Thus, you cannot generally use standard window traversal to find the window passed into a (modal) dialog's constructor. However, MFC records the
CWnd(-derived) class instance you pass into yourCOptionsDialogconstructor and stores it in aprotectedmember variablem_pParentWnd, inherited from theCDialogclass.As long as
COptionsDialogderivespublic/protectedfromCDialogorCDialogEx, the implementation can access this class member.The following
OnInitDialogimplementation will do what you're looking for:There are other options available. For example, you could supply a
COptionsDialogconstructor that takes both aCWnd*and aCSquaresDoc*, delegating the first onto the base class c'tor and storing the document pointer in a (private) class member. This makes for code that's easier to follow in that it explicitly spells out, that the dialog depends on the document.