Graphics.MeasureString 可以計(jì)算出指定字符串在給定字體Font的尺寸SizeF,它的計(jì)算有坑:如果把字符串拆開(kāi)成一個(gè)一個(gè)單字字符串并逐個(gè)計(jì)算尺寸,然后把Width加起來(lái),你會(huì)發(fā)現(xiàn)并不一定等于完整的字符串計(jì)算出來(lái)的Width。
經(jīng)過(guò)一番折騰,最終發(fā)現(xiàn)關(guān)鍵在于字符串中是否有空格。
舉個(gè)例子
Graphics g = Graphics.FromHwnd(IntPtr.Zero);
string foo = "ab c";
float totalCharWidth = 0F;
for (int i = 0; i < foo.Length; i++)
{
float charWidth = g.MeasureString(foo.Substring(i, 1), SystemFonts.DefaultFont, 9999, StringFormat.GenericTypographic).Width;
Console.WriteLine(string.Format("Char '{0}' width : {1}", foo.Substring(i, 1), charWidth));
totalCharWidth += charWidth;
}
Console.WriteLine(string.Format("Total Char Width : {0}", totalCharWidth));
Console.WriteLine(string.Format("String '{0}' Width : {1}", foo, g.MeasureString(foo, SystemFonts.DefaultFont, 9999, StringFormat.GenericTypographic).Width));
執(zhí)行結(jié)果
Char 'a' width : 6
Char 'b' width : 6
Char ' ' width : 0
Char 'c' width : 6
Total Char Width : 18
String 'ab c' Width : 24
字符串foo拆開(kāi)后計(jì)算出來(lái)的Width總和為16,和foo完整計(jì)算出來(lái)Width24不同,關(guān)鍵問(wèn)題顯然是空格的Width居然為0。
經(jīng)過(guò)測(cè)試,Graphics.MeasureString 計(jì)算字符串Width時(shí)會(huì)忽略掉頭尾的空格后再進(jìn)行計(jì)算,而夾在字符串中間的空格卻會(huì)納入計(jì)算(等于幫你給字符串自動(dòng)做了次.Trim(),這坑是什么操作?),因此單獨(dú)計(jì)算空格的Width實(shí)際上計(jì)算的空字符串的Width,因此為0。
所以,如果你希望單獨(dú)得到空格的準(zhǔn)確Width,簡(jiǎn)單的方法是:
1.計(jì)算出"a a"的Width1 => w1;
2.計(jì)算出"aa"的Width => w2;
3.用w1 - w2,就可以得到空格的Width。