HighTechTalks DotNet Forums  

.NET FW v1.1 Listview flickering issue

Dotnet Framework (WinForms Controls) microsoft.public.dotnet.framework.windowsforms.controls


Discuss .NET FW v1.1 Listview flickering issue in the Dotnet Framework (WinForms Controls) forum.



Reply
 
Thread Tools Search this Thread Display Modes
  #1  
Old   
Richard
 
Posts: n/a

Default .NET FW v1.1 Listview flickering issue - 11-16-2007 , 09:33 AM






Hello community,

I need a way to reduce flickering of the listview in .NET FW v1.1.

The case: I have a listview control hosted in a plain form that has 20 rows
and 5 columns. The data for a few of these rows changes often, about 2 times
per second. The effect: the listview flickers each row where the data has
been updated. If a window partial covers the listview, then the entire
listview flickers, regardless whether any data within it has changed.

I have tried several combinations of DoubleBuffer, UserPaint,
AllPaintingInWmPaint, WM_SETREDRAW, LockWindowUpdate, etc... even tried
doing a side-by-side of the listview between 1.1 and 2.0 (fails due to
imcompatibility of CLR), ... and nothing seems to help.

In .NET 2.0, All is fine once I apply the OptimizedDoubleBuffer.

Any way to do this? What can be done to achieve the same effects of the
OptmizedDoubleBuffer in .NET 2.0, but in .NET FW v1.1?

Thank you,


Reply With Quote
  #2  
Old   
Linda Liu[MSFT]
 
Posts: n/a

Default RE: .NET FW v1.1 Listview flickering issue - 11-19-2007 , 02:47 AM






Hi Richard,

The ListView in .NET 1.x doesn't support double buffering. So it's no use
setting the DoubleBuffer style to true for the ListView in .NET 1.x.

In fact, the reason why the ListView flickers when it is updated frequently
is that the WM_ERASEBKGND message is sent to the ListView every time the
ListView needs redrawing. Thus, the ListView items are erased with the back
color first and then redraw the text in them.

To reduce the flickering, we can intercepting the WM_ERASEBKGND message in
the WndProc method of a ListView derived class and clip all the bounds of
the ListView items out of the drawing region, so that the bounds of the
ListView items will not erased with back color and the flickering
disappears.

The following is a sample code:

using System.Windows.Forms;
using System.Drawing;

public class MyListView:ListView
{
int WM_ERASEBKGND=0x14;

protected override void WndProc(ref Message m)
{
if(m.Msg == WM_ERASEBKGND)
{
Color backColor = Enabled ? BackColor :
Color.FromKnownColor(KnownColor.Control);
// create a graphics object using the supplied handle to the device
context.
Graphics graphics = Graphics.FromHdc(m.WParam);
// clip all of the list view items out of the drawing region
foreach (ListViewItem item in Items)
{
graphics.ExcludeClip(new Rectangle(item.Bounds.Left +
2,item.Bounds.Top,item.Bounds.Width-2,item.Bounds.Height));
}
// now paint what's left with the background color
using(SolidBrush brush = new SolidBrush(backColor))
{
graphics.FillRegion(brush, graphics.Clip);
graphics.Dispose();
}
}
else
{
base.WndProc (ref m);
}
}

}

The above code works well on my side. Please try it in your project to see
if it could solve the problem and let me know the result.

Sincerely,
Linda Liu
Microsoft Online Community Support

==================================================
Get notification to my posts through email? Please refer to
http://msdn.microsoft.com/subscripti...ult.aspx#notif
ications.

Note: The MSDN Managed Newsgroup support offering is for non-urgent issues
where an initial response from the community or a Microsoft Support
Engineer within 1 business day is acceptable. Please note that each follow
up response may take approximately 2 business days as the support
professional working with you may need further investigation to reach the
most efficient resolution. The offering is not appropriate for situations
that require urgent, real-time or phone-based interactions or complex
project analysis and dump analysis issues. Issues of this nature are best
handled working with a dedicated Microsoft Support Engineer by contacting
Microsoft Customer Support Services (CSS) at
http://msdn.microsoft.com/subscripti...t/default.aspx.
==================================================

This posting is provided "AS IS" with no warranties, and confers no rights.


Reply With Quote
  #3  
Old   
Richard
 
Posts: n/a

Default RE: .NET FW v1.1 Listview flickering issue - 11-19-2007 , 10:34 AM



Hello Linda,

Works ok in a simple test program, but isn't really in our application...
it still flickers; and even more if the the window is partially hidden, or
when spy++ is connected.

Our listview has the grid style drawing enabled. Is there a way now to turn
off or delay drawing (i.e. would WM_SETDREDRAW work here)?

Thank you,

"Linda Liu[MSFT]" wrote:

Quote:
Hi Richard,

The ListView in .NET 1.x doesn't support double buffering. So it's no use
setting the DoubleBuffer style to true for the ListView in .NET 1.x.

In fact, the reason why the ListView flickers when it is updated frequently
is that the WM_ERASEBKGND message is sent to the ListView every time the
ListView needs redrawing. Thus, the ListView items are erased with the back
color first and then redraw the text in them.

To reduce the flickering, we can intercepting the WM_ERASEBKGND message in
the WndProc method of a ListView derived class and clip all the bounds of
the ListView items out of the drawing region, so that the bounds of the
ListView items will not erased with back color and the flickering
disappears.

The following is a sample code:

using System.Windows.Forms;
using System.Drawing;

public class MyListView:ListView
{
int WM_ERASEBKGND=0x14;

protected override void WndProc(ref Message m)
{
if(m.Msg == WM_ERASEBKGND)
{
Color backColor = Enabled ? BackColor :
Color.FromKnownColor(KnownColor.Control);
// create a graphics object using the supplied handle to the device
context.
Graphics graphics = Graphics.FromHdc(m.WParam);
// clip all of the list view items out of the drawing region
foreach (ListViewItem item in Items)
{
graphics.ExcludeClip(new Rectangle(item.Bounds.Left +
2,item.Bounds.Top,item.Bounds.Width-2,item.Bounds.Height));
}
// now paint what's left with the background color
using(SolidBrush brush = new SolidBrush(backColor))
{
graphics.FillRegion(brush, graphics.Clip);
graphics.Dispose();
}
}
else
{
base.WndProc (ref m);
}
}

}

The above code works well on my side. Please try it in your project to see
if it could solve the problem and let me know the result.

Sincerely,
Linda Liu
Microsoft Online Community Support

==================================================
Get notification to my posts through email? Please refer to
http://msdn.microsoft.com/subscripti...ult.aspx#notif
ications.

Note: The MSDN Managed Newsgroup support offering is for non-urgent issues
where an initial response from the community or a Microsoft Support
Engineer within 1 business day is acceptable. Please note that each follow
up response may take approximately 2 business days as the support
professional working with you may need further investigation to reach the
most efficient resolution. The offering is not appropriate for situations
that require urgent, real-time or phone-based interactions or complex
project analysis and dump analysis issues. Issues of this nature are best
handled working with a dedicated Microsoft Support Engineer by contacting
Microsoft Customer Support Services (CSS) at
http://msdn.microsoft.com/subscripti...t/default.aspx.
==================================================

This posting is provided "AS IS" with no warranties, and confers no rights.



Reply With Quote
  #4  
Old   
Linda Liu[MSFT]
 
Posts: n/a

Default RE: .NET FW v1.1 Listview flickering issue - 11-20-2007 , 05:46 AM



Hi Richard,

Thank you for your prompt reply!

Sorry that I made a mistake in my previous reply, i.e. I said the ListView
in .NET 1.x doesn't support double buffering.

In fact, the ListView class in .NET Framework is a wrapper of the native
ListView control and the native ListView control on Windows XP and later
supports double buffering. Although the ListView in .NET 1.x doesn't
provide the DoubleBuffered property, we can use Win32 API SendMessage
function to set the ListView to use double buffering.

To use the native ListView control, call Application.EnableVisualStyles
before you start your main message loop in the static Main method. The
following is a sample:

public class Form1 : System.Windows.Forms.Form
{
[STAThread]
static void Main()
{
Application.EnableVisualStyles();
Application.Run(new Form1());
}
}

public class MyListView:ListView
{

const int LVM_FIRST=0x1000;
const int LVM_SETEXTENDEDLISTVIEWSTYLE = LVM_FIRST+54;
const int LVS_EX_DOUBLEBUFFER = 0x10000;
[DllImport("user32.dll")]
static extern int SendMessage(IntPtr hWnd, int msg, int wParam,int lParam);

public MyListView()
{
this.SetStyle(ControlStyles.DoubleBuffer,true);
}
public void SetDoubleBuffered()
{

SendMessage(this.Handle,LVM_SETEXTENDEDLISTVIEWSTY LE,LVS_EX_DOUBLEBUFFER,LVS
_EX_DOUBLEBUFFER);
}
protected override void OnHandleCreated(System.EventArgs e)
{
base.OnHandleCreated (e);
this.SetDoubleBuffered();
}
}

Note that the above workaround only applies to Windows XP and later.

Please try it in your project to see if it solves the problem and let me
know the result.

Sincerely,
Linda Liu
Microsoft Online Community Support


Reply With Quote
  #5  
Old   
Richard
 
Posts: n/a

Default RE: .NET FW v1.1 Listview flickering issue - 11-20-2007 , 01:55 PM



Hello Linda,

Yes that did the trick. Thank you. It be nice to have this included in the
documentation!

Richard

"Linda Liu[MSFT]" wrote:

Quote:
Hi Richard,

Thank you for your prompt reply!

Sorry that I made a mistake in my previous reply, i.e. I said the ListView
in .NET 1.x doesn't support double buffering.

In fact, the ListView class in .NET Framework is a wrapper of the native
ListView control and the native ListView control on Windows XP and later
supports double buffering. Although the ListView in .NET 1.x doesn't
provide the DoubleBuffered property, we can use Win32 API SendMessage
function to set the ListView to use double buffering.

To use the native ListView control, call Application.EnableVisualStyles
before you start your main message loop in the static Main method. The
following is a sample:

public class Form1 : System.Windows.Forms.Form
{
[STAThread]
static void Main()
{
Application.EnableVisualStyles();
Application.Run(new Form1());
}
}

public class MyListView:ListView
{

const int LVM_FIRST=0x1000;
const int LVM_SETEXTENDEDLISTVIEWSTYLE = LVM_FIRST+54;
const int LVS_EX_DOUBLEBUFFER = 0x10000;
[DllImport("user32.dll")]
static extern int SendMessage(IntPtr hWnd, int msg, int wParam,int lParam);

public MyListView()
{
this.SetStyle(ControlStyles.DoubleBuffer,true);
}
public void SetDoubleBuffered()
{

SendMessage(this.Handle,LVM_SETEXTENDEDLISTVIEWSTY LE,LVS_EX_DOUBLEBUFFER,LVS
_EX_DOUBLEBUFFER);
}
protected override void OnHandleCreated(System.EventArgs e)
{
base.OnHandleCreated (e);
this.SetDoubleBuffered();
}
}

Note that the above workaround only applies to Windows XP and later.

Please try it in your project to see if it solves the problem and let me
know the result.

Sincerely,
Linda Liu
Microsoft Online Community Support



Reply With Quote
  #6  
Old   
Linda Liu[MSFT]
 
Posts: n/a

Default RE: .NET FW v1.1 Listview flickering issue - 11-20-2007 , 11:15 PM



Hi Richard,

Thank you for your feedback and I am glad to hear that the problem is
fixed.

I will make a suggestion to our documentation team about including this tip
in the documentation.

Thank you for reminding and support for Microsoft!

If you have any other questions in the future, please don't hesitate to
contact us. It's always our pleasure to be of assistance!

Sincerely,
Linda Liu
Microsoft Online Community Support


Reply With Quote
  #7  
Old   
Richard
 
Posts: n/a

Default RE: .NET FW v1.1 Listview flickering issue - 11-30-2007 , 09:59 AM



Hello Linda,

The fix is OK until it made it to quality testing. The fix actually breaks
icons in listviews and treeviews all over. Listviews that have icons now
eeither do not show them altogether or show the wrong ones.

Please advise, thank you,

Richard

"Linda Liu[MSFT]" wrote:

Quote:
Hi Richard,

Thank you for your feedback and I am glad to hear that the problem is
fixed.

I will make a suggestion to our documentation team about including this tip
in the documentation.

Thank you for reminding and support for Microsoft!

If you have any other questions in the future, please don't hesitate to
contact us. It's always our pleasure to be of assistance!

Sincerely,
Linda Liu
Microsoft Online Community Support



Reply With Quote
  #8  
Old   
Linda Liu[MSFT]
 
Posts: n/a

Default RE: .NET FW v1.1 Listview flickering issue - 12-03-2007 , 04:41 AM



Hi Richard,

I performed a test based on your description on my Windows XP machine and
did see the problem.

I searched in our internal database and found that this is a known issue in
Windows XP. The possible workaround to this problem would have been to
custom draw the ListView control if the ListView in .NET 1.x supported
custom drawing. Unfortunately, in fact the ListView in .NET 1.x doesn't
support custom drawing at all.

I will consult this problem in our internal discussion group to see if
there's any workaround.

In addition, if you could upgrade to .NET 2.0, the problem will not exist.

Sincerely,
Linda Liu
Microsoft Online Community Support


Reply With Quote
  #9  
Old   
Richard
 
Posts: n/a

Default RE: .NET FW v1.1 Listview flickering issue - 12-03-2007 , 08:49 AM



Hello Linda,

Going to .NET 2.0 is not an option on this project. If it were, I'd already
be on it :-)

It seems that doing a Application.DoEvents() right after the
Application.EnableVisualStyles() before the creation of the main message loop
has "resolved" the issue (up until QA gets their hands on it).

Please let me know of your internal discussion group outputs. Would this be
the right time to talk about a hotfix?

Thank you

Richard

"Linda Liu[MSFT]" wrote:

Quote:
Hi Richard,

I performed a test based on your description on my Windows XP machine and
did see the problem.

I searched in our internal database and found that this is a known issue in
Windows XP. The possible workaround to this problem would have been to
custom draw the ListView control if the ListView in .NET 1.x supported
custom drawing. Unfortunately, in fact the ListView in .NET 1.x doesn't
support custom drawing at all.

I will consult this problem in our internal discussion group to see if
there's any workaround.

In addition, if you could upgrade to .NET 2.0, the problem will not exist.

Sincerely,
Linda Liu
Microsoft Online Community Support



Reply With Quote
  #10  
Old   
Linda Liu[MSFT]
 
Posts: n/a

Default RE: .NET FW v1.1 Listview flickering issue - 12-07-2007 , 03:25 AM



Hi Richard,

I have received a reply from our internal discussion group. The reply said
that this is an issue of common control v6 issue in .NET 1.1 applications.

Since calling Application.DoEvents after calling
Application.EnableVisualStyles could solve the problem, a hot fix request
would likely be rejected.

Thank you for sharing the workaround in the community. It will definitely
benefit all of us!

If you have any other questions in the future, please don't hesitate to
contact us. It's always our pleasure to be of assistance!

Have a nice weekend!

Sincerely,
Linda Liu
Microsoft Online Community Support


Reply With Quote
Reply




Thread Tools Search this Thread
Search this Thread:

Advanced Search
Display Modes

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

vB code is On
Smilies are On
[IMG] code is On
HTML code is Off



Powered by vBulletin Version 3.5.4
Copyright ©2000 - 2008, Jelsoft Enterprises Ltd.