如何避免ListView列宽调整过程中的界面动态变化与闪烁?
解决ListView列宽调整时的视觉闪烁问题
连续调用两次AutoResizeColumns会触发两次控件重绘,导致你看到列宽先缩后放的闪烁效果。以下是几种有效解决方法:
方法一:通过Win32消息暂停控件重绘
这是最直接的方案,通过发送WM_SETREDRAW消息阻止控件在调整期间重绘,完成后再恢复并强制刷新:
首先声明Win32 API:
[DllImport("user32.dll")] private static extern int SendMessage(IntPtr hWnd, int wMsg, bool wParam, int lParam); private const int WM_SETREDRAW = 0x000B;
然后在列宽调整前后调用:
// 停止控件重绘 SendMessage(lvProps.Handle, WM_SETREDRAW, false, 0); // 执行两次列宽调整 lvProps.AutoResizeColumns(ColumnHeaderAutoResizeStyle.ColumnContent); lvProps.AutoResizeColumns(ColumnHeaderAutoResizeStyle.HeaderSize); // 恢复重绘并强制刷新界面 SendMessage(lvProps.Handle, WM_SETREDRAW, true, 0); lvProps.Refresh();
方法二:使用WinForms的布局暂停方法(备选)
如果不想引入Win32 API,可以尝试用SuspendLayout和ResumeLayout,它能暂停控件的布局逻辑更新,减少闪烁:
lvProps.SuspendLayout(); lvProps.AutoResizeColumns(ColumnHeaderAutoResizeStyle.ColumnContent); lvProps.AutoResizeColumns(ColumnHeaderAutoResizeStyle.HeaderSize); // true参数表示恢复后立即刷新布局 lvProps.ResumeLayout(true);
原理说明
两次AutoResizeColumns调用各自会触发一次控件重绘,暂停重绘后,所有调整操作都会在后台完成,最后一次性刷新界面,用户就不会看到中间的过渡状态了。
内容的提问来源于stack exchange,提问作者Maury Markowitz
相关产品推荐
相关产品推荐

