CodeGuru Home VC++ / MFC / C++ .NET / C# Visual Basic VB Forums Developer.com
Results 1 to 5 of 5
  1. #1
    Join Date
    Dec 2005
    Posts
    52

    How to optimize painting while scrolling (flickering problem)?

    To simplify scrolling operation, I built my own CScrollableWnd, which acted just as a container window, and took advantage of this CScrollHelper (http://www.codeproject.com/KB/dialog...g_support.aspx). Meanwhile, a child shadow window, which contains real content, was included in that container window. The result would be as simple as scrolling entire shadow window, without be concerning for painting content with recalculated coordinates.
    It so far worked well with just one problem, it flickered quite much, visually bothering.

    Here's my code sample, I put some debugging code out there,
    Code:
    void CScrollHelper::OnVScroll(UINT nSBCode, UINT nPos, CScrollBar* pScrollBar)
    {
        // calculate what position I'm about to go
        
        // Scroll the window if needed.
        if ( deltaPos != 0 )
        {
            m_scrollPos.cy += deltaPos;
            m_attachWnd->SetScrollPos(SB_VERT, m_scrollPos.cy, TRUE);
            
            // set SW_SCROLLCHILDREN to have shadow window scrolled
            // m_attachWnd is that container window
            m_attachWnd->ScrollWindowEx(0, -deltaPos, NULL, NULL, NULL, NULL, SW_INVALIDATE | SW_SCROLLCHILDREN);
        }
    }
    
    void CSrollableWindow::OnPaint()
    {
        CPaintDC dc(this); // device context for painting
        // TODO: Add your message handler code here
        // Do not call CWnd::OnPaint() for painting messages
    
        OutputDebugString(_T("on parent window painting..."));
    }
    
    void CShadowWindow::OnPaint()
    {
        CPaintDC dc(this); // device context for painting
        // TODO: Add your message handler code here
        // Do not call __super::OnPaint() for painting messages
    
        OutputDebugString(_T("on shadow window painting..."));
        
        drawSomething(dc);
    }
    I printed the messages received to check out what happened, then ended up with following conclusion.
    [3840] on vertical scrolling...
    [3840] on shadow window painting...
    [3840] on vertical scrolling...
    [3840] on shadow window painting...
    [3840] on vertical scrolling...
    [3840] on shadow window painting...
    [3840] on vertical scrolling...
    [3840] on shadow window painting...
    [3840] on vertical scrolling...
    [3840] on shadow window painting...
    [3840] on vertical scrolling...
    [3840] on shadow window painting...
    [3840] on vertical scrolling...

    It clearly explained why it was so flickering.
    But I'm wondering that why OnPaint was immediately invoked every time. I thought it's supposed to paint only once when I finished scrolling and released mouse.

    How could I do to eliminate flicker?
    thx in advance

  2. #2
    Join Date
    Feb 2005
    Posts
    2,160

    Re: How to optimize painting while scrolling (flickering problem)?

    A scrolling window will invalidate the newly exposed rectangle and if you are just repainting the whole screen on WM_PAINT, then you can get flicker. Is your shadow window a proper child of the scrollable window? You may be able to eliminate flicker with WS_CLIPCHILDREN style applied to the parent window.

  3. #3
    Join Date
    May 2006
    Location
    Dresden, Germany
    Posts
    458

    Re: How to optimize painting while scrolling (flickering problem)?

    Hi,

    In your OnVScroll handler:
    You are calling SetScrollPos with the last param (bRedraw) set to True.
    Then you're calling ScrollWindowEx with the SW_INVALIDATE flag set.

    Both calls will result in sending painting messages to the window specified.

    If you want to reduce flickering:
    Set these Redraw flags only if they're really necessary. E.g. if you have complex scrolling tasks to do: Call all the functions without forcing Windows to repaint the window. After all call once UpdateWindow.

    With regards
    Programartist

  4. #4
    Join Date
    Apr 2004
    Location
    England, Europe
    Posts
    2,492

    Re: How to optimize painting while scrolling (flickering problem)?

    I once implemented flicker-free scrolling by using ScrollWindowEx and only drawing the newly revealed part of the document.
    My hobby projects:
    www.rclsoftware.org.uk

  5. #5
    Join Date
    Dec 2005
    Posts
    52

    Re: How to optimize painting while scrolling (flickering problem)?

    Quote Originally Posted by hoxsiew View Post
    A scrolling window will invalidate the newly exposed rectangle and if you are just repainting the whole screen on WM_PAINT, then you can get flicker. Is your shadow window a proper child of the scrollable window? You may be able to eliminate flicker with WS_CLIPCHILDREN style applied to the parent window.
    I did set WS_CLIPCHILDDREN, not really helped.

    Actually I don't care how many WM_PAINT was sent there, WM_PAINT is lowest priority message and is supposed to be combined by system.

    Now I got 50% speed up with drawing content into to a memory dc first and copying back then.

    thx you all.

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  





Click Here to Expand Forum to Full Width

Featured