我的自定义控件如下:
using System;
using System.Drawing;
using System.Windows.Forms;
using System.ComponentModel;
using System.Runtime.InteropServices;
namespace CustomControls
{
public partial class TrackBarPercent : TrackBar
{
/// <summary>
/// Initializes a new instance of <see cref="TrackBarPercent"/>.
/// </summary>
public TrackBarPercent() : base()
{
InitializeComponent();
SetStyle(ControlStyles.AllPaintingInWmPaint, true);
}
private Font _percentFont = SystemFonts.DefaultFont;
private Color _percentColor = Color.Black;
private SolidBrush _drawBrush = new SolidBrush(Color.Black);
/// <summary>
/// Gets or sets the font of the percent text.
/// </summary>
[Description("Gets or sets the font of the percent text.")]
[Browsable(true)]
public Font PercentFont
{
get { return _percentFont; }
set { _percentFont = value; }
}
/// <summary>
/// Gets or sets the color of the percent text.
/// </summary>
[Description("Gets or sets the color of the percent text.")]
[Browsable(true)]
public Color PercentColor
{
get { return _percentColor; }
set { _percentColor = value; _drawBrush = new SolidBrush(_percentColor); }
}
private Rectangle Slider
{
get
{
try
{
RECT rc = new RECT();
SendMessageRect(this.Handle, TBM_GETTHUMBRECT, IntPtr.Zero, ref rc);
return new Rectangle(rc.left, rc.top, rc.right - rc.left, rc.bottom - rc.top);
}
catch
{
return new Rectangle();
}
}
}
private const int TBM_GETTHUMBRECT = 0x400 + 25;
private struct RECT { public int left, top, right, bottom; }
[DllImport("user32.dll", EntryPoint = "SendMessageW")]
private static extern IntPtr SendMessageRect(IntPtr hWnd, int msg, IntPtr wp, ref RECT lp);
private int lastValue = 0;
protected override void WndProc(ref Message m)
{
try
{
base.WndProc(ref m);
if (m.Msg == 0x0F)
{
if (this.Value != lastValue)
{
lastValue = this.Value;
this.Invalidate();
}
using (Graphics graphics = Graphics.FromHwnd(Handle))
{
DrawPercentText(graphics);
}
}
}
catch { }
}
private void DrawPercentText(Graphics g)
{
try
{
Point pctTxtPoint;
if (this.Orientation == System.Windows.Forms.Orientation.Horizontal)
{
pctTxtPoint = new Point((Slider.Left + Slider.Right) / 2, Slider.Bottom);
}
else
{
pctTxtPoint = new Point(Slider.Right + 5, Slider.Top - 2);
}
double percent = (double)this.Value * 100.0 / (double)this.Maximum;
string pctStr = string.Format("{0:0.##}%", percent);
g.DrawString(pctStr, _percentFont, _drawBrush, pctTxtPoint);
}
catch { }
}
[DllImport("user32.dll")]
public extern static int SendMessage(IntPtr hWnd, uint msg, int wParam, int lParam);
private static int MakeParam(int loWord, int hiWord)
{
return (hiWord << 16) | (loWord & 0xffff);
}
protected override void OnGotFocus(EventArgs e)
{
base.OnGotFocus(e);
SendMessage(this.Handle, 0x0128, MakeParam(1, 0x1), 0);
}
}
}
这在大多数情况下都有效,但每次将鼠标悬停在滑块上时文本都会重新绘制,导致文本看起来很粗体。当另一个控件获得焦点时,此效果消失。另外,我得到了我不理解的控件抛出的定期异常。
我会跟踪为此控件设置的最后一个值,以便在值已更改时使视图无效。我需要这个来阻止控件在前一个文本上绘制百分比文本。我不认为这种做法非常优雅,但我不确定如何做得更好。
如何修复此代码,以便文本不会变为&#34;粗体&#34;并修复我得到的例外情况?