|
-
October 25th, 2010, 01:25 AM
#1
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
-
October 25th, 2010, 07:52 AM
#2
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.
-
October 25th, 2010, 07:56 AM
#3
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
-
October 25th, 2010, 01:40 PM
#4
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.
-
October 27th, 2010, 03:51 AM
#5
Re: How to optimize painting while scrolling (flickering problem)?
 Originally Posted by hoxsiew
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
-
Forum Rules
|
Click Here to Expand Forum to Full Width
|