Overriding OnSize in class derived from CSplitterWnd

I have a splitter window (CCustomSplitterWnd) embedded in a CWnd.  I have written my own version of Create so that before the view is created, the splitter is resized to the size of its parent using MoveWindow.
The problem is that CSplitterWnd's implementation of OnSize calls RecalcLayout, which fails because there is no view to layout.  
My solution was to override OnSize in CCustomSplitterWnd and not call RecalcLayout when I MoveWindow (using a bool flag).
The resulting problem is that my implementation is not getting called.  It's still calling CSplitterWnd::OnSize.  I have rebuilt all and double checked my declaration in the AFX_MSG_MAP.  I will post my source in a comment
LVL 1
sosedadaAsked:
Who is Participating?
I wear a lot of hats...

"The solutions and answers provided on Experts Exchange have been extremely helpful to me over the last few years. I wear a lot of hats - Developer, Database Administrator, Help Desk, etc., so I know a lot of things but not a lot about one thing. Experts Exchange gives me answers from people who do know a lot about one thing, in a easy to use platform." -Todd S.

sosedadaAuthor Commented:
Edited text of question.
0
sosedadaAuthor Commented:
//CustomSplitWnd.h

class CCustomSplitWnd : public CSplitterWnd
{
      DECLARE_DYNAMIC(CCustomSplitWnd)

// Implementation
public:
      CCustomSplitWnd(bool allow_sizing = false);
      virtual ~CCustomSplitWnd();

      //for dynamic ones
      virtual bool CustomCreate(CWnd* pParentWnd,
                                int nMaxRows, int nMaxCols, SIZE sizeMin,
                                CCreateContext* pContext, DWORD dwStyle=WS_CHILD | WS_VISIBLE | SPLS_DYNAMIC_SPLIT);

      void ChangeViewClass(CRuntimeClass *pNewView)
      {
            m_pDynamicViewClass = pNewView;
      }

      // Generated message map functions
      //{{AFX_MSG(CCustomSplitWnd)
      afx_msg UINT OnNcHitTest(CPoint point);
      afx_msg void OnSize(UINT nType, int cx, int cy);
      //}}AFX_MSG
      DECLARE_MESSAGE_MAP()

public:
      // for customizing DYNAMIC_SPLIT behavior
      // default asserts that it is deleting a view.
      virtual void DeleteView(int row, int col);

private:
      bool m_bResizable;
      bool m_bDeferRecalcLayout;
};

//returns the id of the pane this view is in
//will return AFX_IDW_PANE_FIRST if not in a splitter
extern int GetViewIDFromParentSplitter(CWnd* view);


//CustomSplitWnd.cpp
#include "stdafx.h"
#include "CustomSplitWnd.h"


IMPLEMENT_DYNAMIC(CCustomSplitWnd, CSplitterWnd)

BEGIN_MESSAGE_MAP(CCustomSplitWnd, CSplitterWnd)
      //{{AFX_MSG_MAP(CPCAcqSplitWnd)
      ON_WM_NCHITTEST()
      //}}AFX_MSG_MAP
END_MESSAGE_MAP()


CCustomSplitWnd::CCustomSplitWnd(bool allow_sizing):
      m_bResizable(allow_sizing),
      m_bDeferRecalcLayout(false)
{
      if (!m_bResizable)
      {
      /*      m_cxSplitter=3;      // put your own values here, to make the splitter fit your needs
            m_cySplitter=3;
            m_cxBorderShare=0;
            m_cyBorderShare=0;      
            m_cxSplitterGap=3;
            m_cySplitterGap=3;*/
      }
}

CCustomSplitWnd::~CCustomSplitWnd()
{
}

bool CCustomSplitWnd::CustomCreate(CWnd* pParentWnd,
                                                   int nMaxRows, int nMaxCols, SIZE sizeMin,
                                                   CCreateContext* pContext, DWORD dwStyle/*, UINT nID*/)
{
      ASSERT(pParentWnd != NULL);
      ASSERT(sizeMin.cx > 0 && sizeMin.cy > 0);   // minimum must be non-zero

      ASSERT(pContext != NULL);
      ASSERT(pContext->m_pNewViewClass != NULL);
      ASSERT(dwStyle & WS_CHILD);
      ASSERT(dwStyle & SPLS_DYNAMIC_SPLIT);   // must have dynamic split behavior

      // Dynamic splitters are limited to 2x2
      ASSERT(nMaxRows >= 1 && nMaxRows <= 2);
      ASSERT(nMaxCols >= 1 && nMaxCols <= 2);
      ASSERT(nMaxCols > 1 || nMaxRows > 1);       // 1x1 is not permitted

      UINT nID = GetViewIDFromParentSplitter(pParentWnd);

      m_nMaxRows = nMaxRows;
      m_nMaxCols = nMaxCols;
      ASSERT(m_nRows == 0 && m_nCols == 0);       // none yet
      m_nRows = m_nCols = 1;      // start off as 1x1
      if (!CreateCommon(pParentWnd, sizeMin, dwStyle, nID))
            return false;
      ASSERT(m_nRows == 1 && m_nCols == 1);       // still 1x1

      CRect rect;
      pParentWnd->GetClientRect(&rect);

      m_bDeferRecalcLayout = true;
      MoveWindow(0, 0, rect.right, rect.bottom);
      m_bDeferRecalcLayout = false;

      ASSERT(pContext->m_pNewViewClass->IsDerivedFrom(RUNTIME_CLASS(CWnd)));
      m_pDynamicViewClass = pContext->m_pNewViewClass;
            // save for later dynamic creations

      // add the first initial pane
      if (!CreateView(0, 0, m_pDynamicViewClass, sizeMin, pContext))
      {
            DestroyWindow(); // will clean up child windows
            return false;
      }
      m_pColInfo[0].nIdealSize = sizeMin.cx;
      m_pRowInfo[0].nIdealSize = sizeMin.cy;

      return true;
}

void CCustomSplitWnd::OnSize(UINT nType, int cx, int cy)
{
      if (nType != SIZE_MINIMIZED && cx > 0 && cy > 0 && !m_bDeferRecalcLayout)
            RecalcLayout();

      CWnd::OnSize(nType, cx, cy);
}

UINT CCustomSplitWnd::OnNcHitTest(CPoint point)
{
      if (m_bResizable)
            return CSplitterWnd::OnNcHitTest(point);
      else
            return 0; //this stops all messages from getting through
}

void CCustomSplitWnd::DeleteView(int row, int col)
{
      ASSERT_VALID(this);

      // if active child is being deleted - activate next
      CWnd* pPane = GetPane(row, col);
      /*ASSERT_KINDOF(CView, pPane);
      if (GetActivePane() == pPane)
            ActivateNext(FALSE);
*/
      // default implementation assumes view will auto delete in PostNcDestroy
      pPane->DestroyWindow();
      /*didn't work on shutdown, will continue putting delete this in PostNcDestroy()
      if (!pPane->IsKindOf(RUNTIME_CLASS(CView)))
            delete pPane;
            */
}


int GetViewIDFromParentSplitter(CWnd* view)
{
      CSplitterWnd* parent = dynamic_cast<CSplitterWnd*>(view->GetParent());

      if (parent == 0)
            return AFX_IDW_PANE_FIRST;

      int rows, cols;

      rows = parent->GetRowCount();
      cols = parent->GetColumnCount();
      for(int row = 0; row < rows; row++)      
      {
            for(int col = 0; col < cols; col++)            
            {
                  if(view == parent->GetPane(row,col))
                  {
                        return parent->IdFromRowCol(row, col);
                  }
            }
      }

      ASSERT(true == false);
      return 0;
}
0
Gandalf32Commented:
You have to add:

BEGIN_MESSAGE_MAP(CCustomSplitWnd, CSplitterWnd)
//{{AFX_MSG_MAP(CPCAcqSplitWnd)
ON_WM_NCHITTEST()
ON_WM_SIZE()   <-- Added line
//}}AFX_MSG_MAP
END_MESSAGE_MAP()


This adds the event to the window's message map.
0

Experts Exchange Solution brought to you by

Your issues matter to us.

Facing a tech roadblock? Get the help and guidance you need from experienced professionals who care. Ask your question anytime, anywhere, with no hassle.

Start your 7-day free trial
sosedadaAuthor Commented:
DUH!!!!!  I guess thats what happens when you rely on class wizard too much.  Please answer for your points.
0
sosedadaAuthor Commented:
thanks
0
It's more than this solution.Get answers and train to solve all your tech problems - anytime, anywhere.Try it for free Edge Out The Competitionfor your dream job with proven skills and certifications.Get started today Stand Outas the employee with proven skills.Start learning today for free Move Your Career Forwardwith certification training in the latest technologies.Start your trial today
System Programming

From novice to tech pro — start learning today.