这不是一个舍入问题。差异~ 5+像素
测试用例字符串:"MACD (26,12,9) -0.000016"
e.Graphics.MeasureString("MACD (26,12,9) -0.000016", SystemFonts.DefaultFont).Width)
TextRenderer.MeasureText("MACD (26,12,9) -0.000016", SystemFonts.DefaultFont).Width)
结果总是:139.3942
134
为什么大小有这么大的差异?我只需要油漆方法外的字符串的宽度的圆。但是它应该匹配MeasureString,反之亦然
TextRenderer
使用GDI来渲染文本,而Graphics
使用GDI+。两者使用略微不同的方法来布局文本,因此大小不同。
您应该使用哪一个取决于最终将用于实际绘制文本的内容。如果你用GDI+ Graphics.DrawString
画,用Graphics.MeasureString
测量。如果您使用GDI TextRenderer.DrawText
进行绘图,请使用TextRenderer.MeasureText
进行测量。
如果文本将显示在Windows窗体控件中,如果UseCompatibleTextRendering
设置为false
(这是默认值),则使用TextRenderer
。
阅读你的问题的字里行间,你似乎在使用TextRenderer
,因为你在Paint
事件之外没有Graphics
实例。如果是这种情况,您可以自己创建一个来进行测量:
using( Graphics g = someControl.CreateGraphics() )
{
SizeF size = g.MeasureString("some text", SystemFonts.DefaultFont);
}
如果您无法访问控件来创建图形实例,您可以使用此控件为屏幕创建一个,这对于测量目的来说很好。
using( Graphics g = Graphics.FromHwnd(IntPtr.Zero) )
{
SizeF size = g.MeasureString("some text", SystemFonts.DefaultFont);
}
我让下面的类在paint事件之外使用MeasureString,它工作得很好。
public interface ITextMeasurer
{
SizeF MeasureString(string text, Font font, StringFormat format);
}
public class TextMeasurer : ITextMeasurer
{
private readonly Image _fakeImage;
private readonly Graphics _graphics;
public TextMeasurer()
{
_fakeImage = new Bitmap(1, 1);
_graphics = Graphics.FromImage(_fakeImage);
}
public SizeF MeasureString(string text, Font font, StringFormat format)
{
return _graphics.MeasureString(text, font, int.MaxValue, format);
}
}