我最近开始分析我的WinForms应用程序,并注意到在滚动ListView时出现巨大的内存泄漏。C#巨大的内存泄漏当在ListView中使用OwnerDraw/DrawItem滚动时
如果我不通过.OwnerDraw和DrawItem执行我自己的自定义渲染,则不会发生此泄漏。
我的ListView由一个图像,文本和在选定对象上绘制的矩形组成。我错过了一些清理?它似乎是无休止地重绘东西,这就是内存使用量叠加的原因。
如果我连续向上和向下滚动列表,它会在10秒内爬到超过100mb的内存使用量。如果我不使用OwnerDraw,内存使用保持一致。
根据我看到的例子,虽然我的用法似乎有效。
感谢您的任何援助。
// ## Inside form load ## //
listView2.OwnerDraw = true;
listView2.DrawItem += new DrawListViewItemEventHandler(listView2_DrawItem);
// ## How the items are added to the ListView (in form load) ## //
// Create an image list
ImageList imageList = new ImageList();
imageList.ImageSize = new Size(256, 178);
imageList.ColorDepth = ColorDepth.Depth32Bit;
// Assign the image list to the listView
listView2.LargeImageList = imageList;
// Create an array of 20 listView items
ListViewItem[] items = new ListViewItem[20];
// Create 20 items
for (int i = 0; i < 20; i++)
{
// Add the image for this item to the image list
imageList.Images.Add(Image.FromFile("myFile2.jpg"));
// Create the item
items[i] = new ListViewItem("Item");
items[i].ImageIndex = i;
// Add the item to the listView
listView2.Items.Add(icons[i]);
}
// ## Draw item handler ## //
private void listView2_DrawItem(object sender, DrawListViewItemEventArgs e)
{
Rectangle rect3 = new Rectangle(e.Bounds.Left + 10, e.Bounds.Top + 10, 256, 178);
Rectangle rect4 = new Rectangle(rect3.Left, e.Bounds.Top, rect3.Width, e.Bounds.Height + 14);
TextFormatFlags flags = TextFormatFlags.HorizontalCenter |
TextFormatFlags.Bottom | TextFormatFlags.WordBreak;
// Draw the image for this item
e.Graphics.DrawImage(e.Item.ImageList.Images[e.ItemIndex], rect3);
// Draw the text and the surrounding rectangle.
TextRenderer.DrawText(e.Graphics, e.Item.Text, new Font("Arial", 12), rect4, Color.Black, flags);
if (e.Item.Selected)
{
int width = e.Item.ImageList.Images[e.ItemIndex].Width;
int height = e.Item.ImageList.Images[e.ItemIndex].Height;
Brush brush = new SolidBrush(Color.FromArgb(180, 1, 1, 1));
e.Graphics.FillRectangle(brush, rect3);
TextFormatFlags flags2 = TextFormatFlags.HorizontalCenter |
TextFormatFlags.VerticalCenter | TextFormatFlags.WordBreak;
// Draw the text
TextRenderer.DrawText(e.Graphics, e.Item.Text, new Font("Arial", 12), rect3, Color.White, flags2);
}
}
是什么让你觉得你实际上是在泄漏内存(除了字体和画笔)? GC只在需要时设置;所以内存使用量往往会堆积起来,直到那时...... – TaW
我现在要离开任务管理器。如果我不断地上下滚动,它可以在10秒内使用100MB的内存。我相信它是泄漏的,因为它在使用默认图纸时不会发生,只有在我控制图纸时才会发生。我还没有试图继续超过100+ MB,看看它是否被封锁。我担心由于标准格式绘图不会漏出(mem使用率没有随着默认绘制而上升) – PersuitOfPerfection
听起来很正常。在GB RAM和没有竞争程序的机器上,100MB没有任何问题。添加缺少的使用条款,并尝试使其真正达到更大的“泄漏”。 – TaW