TextRenderer.DrawText does Arial differently on XP vs Vista

I have a C # application that does text rendering, something similar to a simple wysiwyg text editor.

I use TextRenderer.DrawText to display the text on the screen and GetTextExtentPoint32 to measure the text so that I can put different font styles / sizes on the same line.

Everything works fine in Vista. In Arial, however, Arial is different in different ways, some characters, such as "o" and "b", take up more space than in Vista. GetTextExtentPoint32 seems to measure the string, as in Vista, but with a smaller width. The end result is that from time to time a run of text overlaps the text that precedes it, because the previous text is measured as less than what it actually is on the screen.

Also, my text rendering code looks like the text is accurate (for easy formatting and only in English) and i.e. visualization of the text seems to be consistent between vista and xp - as I noticed the resizing of different characters.

Anyone have any ideas on what is going on?

In short, TextRenderer.DrawText and GetTextExtentPoint32 do not match xp for Arial. It seems that DrawText has drawn certain characters more and / or less than in Vista, but GetTextExtentPoint32 seems to measure the text in the same way as in Vista (which seems to correspond to the rendering of the text, i.e. on both xp and vista objects). Hope this makes sense.

Note. Unfortunately, TextRenderer.MeasureString is not fast or accurate to fit my requirements. I tried to use it and had to rip it out.

+6
c # text windows-xp windows-vista
source share
3 answers

Thank you for taking the time to answer Adrian.

I understand that TextRenderer.DrawText actually completes the GDI call, completely bypassing GDI + text. This is why I was confused by GetTextExtentPoint32 not jiving with the exit.

I think I found the problem. It turns out that if you set Graphics.TextRenderingHint to System.Drawing.Text.TextRenderingHint.ClearTypeGridFit or possibly other values, this will cause some characters in some fonts to increase or decrease. This seems to be true in XP more than in Vista. I have not seen this at all in Vista. In any case, it seems that GetTextExtentPoint32 is either not able to recognize the difference, or I do not set any flag when making the call.

My solution is to simply use the default textrenderinghint settings for the system.

+2
source share

I'm not a C # guy, but I believe .NET rendering is built on top of GDI +. I'm also sure that GDI + does its own font rendering, which uses fuzzy scaling.

GetTextExtentPoint32 , on the other hand, is part of the GDI. GDI uses size hints that can affect character widths depending on the font size. In general, a GDI text with a small size will look a bit getter, but it will not scale linearly.

You must use one model or the other one after another to get perfect pixel results.

There may be other factors in the game that may make this more obvious in XP than in Vista, but the main problem exists in both. These other factors may include DPI settings, DPI scaling, ClearType or anti-aliasing settings, font binding (if you mix scripts from other alphabets), font replacement (especially in print), and possibly even different versions of Arial. I'm not even sure that GDI + uses the same default display mode as GDI.

Also see my answer to print preview .

0
source share

Actually, both TextRenderer DrawText and MeasureString based on DrawTextEx (and this is a User32 function, not Gdi). Thus, you might consider using your own routed calls for this function instead of MeauseString, as it does additional calculations (especially if you use the override function without HDC).

It is also possible that this post will be useful to you.

0
source share

All Articles