我一直在尝试为现有的 .Net WinForms 控件绘制自定义边框。我通过创建一个类来尝试此操作,该类从我想更改其边框颜色的控件中,然后在绘画过程中尝试几件事。我尝试了以下方法:
1. 抓住WM_NCPAINT
。这有点工作。下面代码的问题是,当控件调整大小时,边框会在右侧和底部被切断。不好。
protected override void WndProc(ref Message m)
{
if (m.Msg == NativeMethods.WM_NCPAINT) {
WmNcPaint(ref m);
return;
}
base.WndProc(ref m);
}
private void WmNcPaint(ref Message m)
{
if (BorderStyle == BorderStyle.None) {
return;
}
IntPtr hDC = NativeMethods.GetWindowDC(m.HWnd);
if (hDC != IntPtr.Zero) {
using (Graphics g = Graphics.FromHdc(hDC)) {
ControlPaint.DrawBorder(g, new Rectangle(0, 0, this.Width, this.Height), _BorderColor, ButtonBorderStyle.Solid);
}
m.Result = (IntPtr)1;
NativeMethods.ReleaseDC(m.HWnd, hDC);
}
}
2. 覆盖void OnPaint
。这适用于某些控件,但不是全部。这也需要您设置BorderStyle
为BorderStyle.None
,并且您必须手动清除油漆上的背景,否则在调整大小时会出现此问题。
protected override void OnPaint(PaintEventArgs e)
{
base.OnPaint(e);
ControlPaint.DrawBorder(e.Graphics, new Rectangle(0, 0, this.Width, this.Height), _BorderColor, ButtonBorderStyle.Solid);
}
3. 覆盖void OnResize
and void OnPaint
(如方法 2)。这样,它可以很好地调整大小,但不是在启用面板时,在这种情况下,向下滚动时AutoScroll
它将看起来像这样。如果我尝试使用WM_NCPAINT
绘制边框,Refresh()
没有任何效果。
protected override void OnResize(EventArgs eventargs)
{
base.OnResize(eventargs);
Refresh();
}
建议非常受欢迎。对于多种类型的控件,我想知道最好的方法是什么(我必须为多个默认的 WinForms 控件执行此操作)。