locked
How do I use DrawFrameControl in a CDIalog? RRS feed

  • Question

  • I want to call DrawFrameControl( rect, DFC_SCROLL, DFCS_SCROLLSIZEGRIP ) to draw a resizable gripper. I have a VS created MFC application (visual studio style) and I took the CAboutDlg that was created by the MFC app wizard. I have implemented OnPaint and set the dialog property so it is resizable. When I run, the dialog is resizable and this code paints the frame control:

    void CAboutDlg::OnPaint()
    {
     CPaintDC dc(this);
     CRect rect;
     // rect of size grip
     GetClientRect(&rect);
     rect.left = rect.right - ::GetSystemMetrics(SM_CXHSCROLL);
     rect.top = rect.bottom - ::GetSystemMetrics(SM_CYVSCROLL);

     dc.DrawFrameControl(rect, DFC_SCROLL, DFCS_SCROLLSIZEGRIP);
     GdiFlush();
    }

    Very simple (that code minus GdiFlush I found on the MSDN as a sample with the API MSDN page).

    But, when I resize the dialog, the display isn't drawing a backgroup over the frame control graphics. So if I size somewhat slowly I get "zingers" spread across the bottom or right edge of the dialog. The area where I am drawing doesn't repaint the background. At least that is what I think is the issue. If I grab the frame and resize, say to make it wider, and do so with quick jerks, the control draws fine but leaves the sequence of draws unerased (thus the "zingers"). Also, if after resizing and seeing the issue, I can simply grab the caption area and move the dialog down off the screen and back up and the display is fine again (just like the initial draw).

    I have played with a myriad of dialog setting using the dialog editor in Visual Studio (clip children/siblings/overlapped vs. popup) but have found nothing that fixes the issue.

    I have run this on Win10 and Win7 with the same issue.

    Anyone have a suggestion as to what to try.


    R.D. Holland

    Tuesday, September 4, 2018 5:33 PM

Answers

  • Try handling the WM_NCCALCSIZE message:

    void CAboutDlg::OnNcCalcSize( BOOL bCalcValidRects, NCCALCSIZE_PARAMS* lpncsp )
    {
       if( bCalcValidRects )
       {
          CRect rect = lpncsp->rgrc[2];
          ScreenToClient( &rect );
          rect.left = rect.right - ::GetSystemMetrics( SM_CXHSCROLL );
          rect.top = rect.bottom - ::GetSystemMetrics( SM_CYVSCROLL );
          InvalidateRect( rect );
       }
    
       CDialogEx::OnNcCalcSize( bCalcValidRects, lpncsp );
    }
    


    • Proposed as answer by Seetharam Wednesday, September 5, 2018 1:48 AM
    • Marked as answer by RD Holland Wednesday, September 5, 2018 12:34 PM
    Tuesday, September 4, 2018 6:52 PM

All replies



  • R.D. Holland


    Here is an image after I resized to make it wider and then taller.
    • Edited by RD Holland Tuesday, September 4, 2018 5:35 PM Add comment
    Tuesday, September 4, 2018 5:34 PM
  • Try handling the WM_NCCALCSIZE message:

    void CAboutDlg::OnNcCalcSize( BOOL bCalcValidRects, NCCALCSIZE_PARAMS* lpncsp )
    {
       if( bCalcValidRects )
       {
          CRect rect = lpncsp->rgrc[2];
          ScreenToClient( &rect );
          rect.left = rect.right - ::GetSystemMetrics( SM_CXHSCROLL );
          rect.top = rect.bottom - ::GetSystemMetrics( SM_CYVSCROLL );
          InvalidateRect( rect );
       }
    
       CDialogEx::OnNcCalcSize( bCalcValidRects, lpncsp );
    }
    


    • Proposed as answer by Seetharam Wednesday, September 5, 2018 1:48 AM
    • Marked as answer by RD Holland Wednesday, September 5, 2018 12:34 PM
    Tuesday, September 4, 2018 6:52 PM
  • Why you want to do that? The new features of MFC allow you to resize the dialog already.

    Steve

    Tuesday, September 4, 2018 7:38 PM
  • Thanks Seetharm! That did it.

    I don't know if it is true but with these "shadowed" windows the NC client area is now mostly outside the actual dialog that is displayed? When I run spyxx and try to highlight a dialog on my WIn10 box, spy lets me click the highlight command but nothing highlights. I can only highlight child controls. After seeing your post I ran spyxx on the window and noted the restored and client rects and then ran print screen to get the dialog and paste it into paint. I know the shadow doesn't capture (probably for the same reason spy can't highlight the window). Then using paint I used the select tool to surround the image with both of the rectangles spyxx showed me. I can see I only have a few pixels of non-client area in the dialog window where I was drawing the control. The rest of what spy calls the rectangle and restored rect (same rects in my cases), falls outside of the image in paint.

    Adding your nccalcsize now lets the frame control paint without zingers.

    Steve,

    We are bringing back the old Windows resize gripper because customers don't like trying to grab a dialog around the shadow. So I already override nc hit test and get the client rect and return HTBOTTOMRIGHT when the cursor is over where I want to draw the gripper.


    R.D. Holland

    Wednesday, September 5, 2018 12:54 PM