Solved

Splitter windows

Posted on 1998-09-03
15
600 Views
Last Modified: 2013-11-20
I am attempting to simulate dynamic splitter windows by creating a new static window as the user requests a new column or row.  The problem is that I can't get the splitter window (which is a child of the MainFrame window)to paint after the new splitter is created.  It will only paint if I minimize and restore.  Here is a section of code for adding a new row:

      delete m_wndSplitter;
      m_wndSplitter = new CSplitterWindow;

      CCreateContext context;
      context.m_pCurrentFrame = this/*MainFrame CWnd*/;

      if (m_nRows < 16)
            m_nRows++;

      BOOL returnVal = m_wndSplitter->CreateStatic(this,                                                                          m_nRows,
                                                                        m_nCols);

      CRect rect;
      GetClientRect(rect);

      int width = rect.right/m_nCols;
      int height = rect.bottom/m_nRows;

      for (int i = 0; i < m_nRows; i++)
      {
            for (int j = 0; j < m_nCols; j++)
            {
                  if (! m_wndSplitter->CreateView(i, j, RUNTIME_CLASS (CSplitterView), CSize(width,height), &context))
                        returnVal = FALSE;
            }
      }

m_wndSplitter is a member of the MainFrame class. I even put a posted a WM_PAINT message to m_wndSplitter at the end of the MainFrame's OnPaint function, but no luck.  Any help would be greatly appreciated.  Thanks
0
Comment
Question by:bmelling9
15 Comments
 

Author Comment

by:bmelling9
ID: 1321676
Edited text of question
0
 
LVL 3

Expert Comment

by:Norbert
ID: 1321677
Did You try m_wndSplitter->Invalidate() ?
0
 
LVL 2

Expert Comment

by:milenvk
ID: 1321678
Replace the lines:

if (! m_wndSplitter->CreateView(i, j, RUNTIME_CLASS (CSplitterView), CSize(width,height), &context))
  returnVal = FALSE;

with:

if (m_wndSplitter->CreateView(i, j, RUNTIME_CLASS (CSplitterView), CSize(width,height), &context))
  RedrawWindow(NULL, NULL, RDW_INVALIDATE | RDW_UPDATENOW | RDW_ERASE | RDW_ALLCHILDREN );
else
  returnVal = FALSE;
0
Problems using Powershell and Active Directory?

Managing Active Directory does not always have to be complicated.  If you are spending more time trying instead of doing, then it's time to look at something else. For nearly 20 years, AD admins around the world have used one tool for day-to-day AD management: Hyena. Discover why

 

Author Comment

by:bmelling9
ID: 1321679
this did not solve the problem- the splitter window is still not getting painted.  I have developed a work around for this situation- I am posting a WM_SIZE to the MainFrame Window at the end of the MainFrame Window's OnPaint function.  However, this seems unnecessary, so I would still be interested in knowing the source of this problem and/or a more logical solution.
0
 
LVL 2

Expert Comment

by:jstolan
ID: 1321680
I've never done a dynamic splitter like your application, but Invalidate() followed by UpdateWindow() will almost always work.
0
 
LVL 6

Expert Comment

by:snoegler
ID: 1321681
CSplitterWnd::RecalcLayout() should be working, i think ...
It is called upon WM_SIZE messages, and should be called after layout changes.
Hope this works :)
0
 
LVL 1

Expert Comment

by:sudhirbrat
ID: 1321682
I think you are not associating the current document to the newly created views.

Give the current document to the context.

context.m_pCurrentDoc = ???//Current Document pointer

Try this.
0
 

Author Comment

by:bmelling9
ID: 1321683
I am not currently working with a document- all I have is a frame window and the splitter window.  I have tried nearly all possible combinations of calling Invalidate() and UpdateWindow() for both as well as RecalcLayout() for the Splitter.  I have also posted WM_PAINT messages to both windows at various points in the process of creating the splitter, but the only thing that has worked is the work around I mentioned in my note on 9/3.  I guess I don't have to have an answer to this, but my curiosity is piqued, so I'm upping the points a little...
0
 
LVL 1

Expert Comment

by:subbaiah
ID: 1321684

Have U tried using UpdateAllViews().
0
 

Expert Comment

by:TangCheng
ID: 1321685
If you want to Create a splitter window use static view, you must  overwrite OnCreateClient(...).
Now I give you this code.I set View is CMyView1 and CMyView2.

//in Hpp File
class CMyFrame : CFrameWnd
{
  .....
  CSplitterWnd m_wndSplitter; //This Value is by AppWizard Create
                              //If you Con't see it,
                              //you can write it
}


//in Cpp File
BOOL CMyFrame::OnCreateClient(LPCREATESTRUCT /*lpcs*/, CCreateContext* pContext)
{
      // TODO: Add your specialized code here and/or call the base class
      if(!m_wndSplitter.CreateStatic(this, 2, 1) ||
         !m_wndSplitter.CreateView(0, 0, RUNTIME_CLASS(CMyView1), CSize(100, 200), pContext) ||
         !m_wndSplitter.CreateView(1, 0, RUNTIME_CLASS(CMyView2), CSize(100, 200), pContext))
         return FALSE;

      return TRUE;
       
        //Don't Call System OnCreateClient(...)
      //return CFrameWnd::OnCreateClient(lpcs, pContext);
}

0
 
LVL 6

Expert Comment

by:snoegler
ID: 1321686
This is the source code of CFrameWnd::OnSize():

(mainfrm.cpp)
void CFrameWnd::OnSize(UINT nType, int cx, int cy)
{
      CWnd::OnSize(nType, cx, cy);    // important for MDI Children
      if (nType != SIZE_MINIMIZED)
            RecalcLayout();
}

You said, when you post a WM_SIZE message at the end of a OnPaint() handler, it works.
Maybe you should try this in your splitter update function:

Invalidate(); // Invalidate client rectangle
UpdateWindow(); // Wait for WM_PAINT to be sent
RecalcLayout(); // called by WM_SIZE

This should have the same effect as what you did in the OnPaint() handler. If this doesn't work,
perhaps you could replace RecalcLayout() with your WM_SIZE posting.
0
 

Author Comment

by:bmelling9
ID: 1321687
I did override the OnCreateClient function and it works when the frame window is created.  The problem occurs after the frame has been created when, in response to a user command, I attempt to delete the static splitter and create another with different dimensions.  
0
 
LVL 6

Expert Comment

by:snoegler
ID: 1321688
When you set up a CCreateContext like the one passed to OnCreateClient, this should work:

C...Frame::OnUserAction()
{
  CCreateContext context;
  // set up context
  ...
 
  m_wndSplitter.DestroyWindow();
 
  // insert here the code part from OnCreateClient which creates the m_wndSplitter

}
0
 

Author Comment

by:bmelling9
ID: 1321689
Thanks snoegler, your comment of 9/13 worked.  I was calling RecalcLayout() on the CSplitterWnd derived class, not the CFrameWnd derived class.  Adding the RecalcLayout() call to the end of my CreateSplitter routine did the trick.  This is my first question at experts exchange, so I don't know how to get you the points for this question since you did not submit an "answer".  Let me know if I need to do anything.  Thanks again.
0
 
LVL 6

Accepted Solution

by:
snoegler earned 70 total points
ID: 1321690
You need to have an open question (which is not yet rejected) to give the points.
So i'll post this here as a dummy :)
Thanks, BTW :)
0

Featured Post

Master Your Team's Linux and Cloud Stack

Come see why top tech companies like Mailchimp and Media Temple use Linux Academy to build their employee training programs.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Suggested Solutions

Title # Comments Views Activity
Excel Use VBA to get user's Mac Address for their computer 5 163
Smart Camera scanning and reading information 3 106
fix34  challenge 9 117
Making an alias 7 95
Introduction: Dialogs (1) modal - maintaining the database. Continuing from the ninth article about sudoku.   You might have heard of modal and modeless dialogs.  Here with this Sudoku application will we use one of each type: a modal dialog …
Introduction: Dialogs (2) modeless dialog and a worker thread.  Handling data shared between threads.  Recursive functions. Continuing from the tenth article about sudoku.   Last article we worked with a modal dialog to help maintain informat…
This video will show you how to get GIT to work in Eclipse.   It will walk you through how to install the EGit plugin in eclipse and how to checkout an existing repository.
With Secure Portal Encryption, the recipient is sent a link to their email address directing them to the email laundry delivery page. From there, the recipient will be required to enter a user name and password to enter the page. Once the recipient …

770 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question