<p>We need to optimize the text rendering for a C# <a href="http://en.wikipedia.org/wiki/Windows_Forms" rel="noreferrer">Windows Forms</a> application displaying a large number of small strings in an irregular grid.  At any time there can be well over 5000 cells visible that update 4 times per second.  The font family and size is consistent across the cells, though the color may vary from cell to cell, as will bold/italic/plain.</p>

<p>I've seen conflicting information on the web about <code>TextRenderer.DrawText</code> vs. <code>Graphics.DrawString</code> being the fastest/best, which reduces to a <a href="http://en.wikipedia.org/wiki/Graphics_Device_Interface" rel="noreferrer">GDI</a> vs. <a href="http://en.wikipedia.org/wiki/Graphics_Device_Interface#GDI.2B" rel="noreferrer">GDI+</a> comparison at the <a href="http://en.wikipedia.org/wiki/Windows_API" rel="noreferrer">Win32</a> level.  </p>

<p>I've also seen radically different results on Windows XP vs. Windows Vista, but my main target is Windows XP.  Articles promising great advances 
under <a href="http://en.wikipedia.org/wiki/.NET_Framework_3.0#.NET_Framework_3.0" rel="noreferrer">WinFX</a> and <a href="http://en.wikipedia.org/wiki/DirectX#DirectX_10" rel="noreferrer">DirectX 10</a> aren't helpful here :-)</p>

<p>What's the best approach here?  I'm not afraid of introducing a small C++/CLI layer and optimizing device context handling to squeeze out more performance, but I'd like some definitive advice about which direction to take.</p>

<p>EDIT:
Thanks for the initial responses.  I'll be trying a combination of background bitmap rendering and sticking with the GDI equivalent calls.</p>

[{'answer_id': 71487, 'author': 'Phil Wright', 'author_id': 6276, 'author_profile': 'https://Stackoverflow.com/users/6276', 'pm_score': 2, 'selected': False, 'text': '<p>GDI is faster at drawing in general that GDI+. I worked on a project that had to draw thousands of lines and text strings and switching from GDI+ to GDI made a significant performance improvement. That was using Windows XP so I cannot comment on Vista. I would also recommend using double buffering for your drawing to also improve performance. Create a compatible off screen bitmap and reuse that each time you need to draw.</p>\n'}, {'answer_id': 71546, 'author': 'Community', 'author_id': -1, 'author_profile': 'https://Stackoverflow.com/users/-1', 'pm_score': 2, 'selected': False, 'text': '<p>5000+ text rendering is slow even with GDI, especially if you need scrolling. Create a separate rendering thread and notify the UI thread every 200 ms and bitblt the current results. It gives a smooth user experience.</p>\n'}, {'answer_id': 71552, 'author': 'Mike Dimmick', 'author_id': 6970, 'author_profile': 'https://Stackoverflow.com/users/6970', 'pm_score': 4, 'selected': True, 'text': '<p>A Microsoft developer has posted a <a href="http://blogs.msdn.com/cjacks/archive/2006/05/19/602021.aspx" rel="noreferrer">GDI vs. GDI+ Text Rendering Performance</a> article on his blog which answers the raw speed question: on his system, GDI DrawText was about 6 times faster than GDI+ DrawString.</p>\n\n<p>If you need to be a real speed demon, TextOut is faster than DrawText, but you\'ll have to take care of clipping and word-wrapping yourself. ExtTextOut supports clipping.</p>\n\n<p>GDI rendering (TextRenderer) will be more consistent with other parts of Windows using GDI; GDI+ tries to be device-independent and so <a href="http://windowsclient.net/articles/gdiptext.aspx" rel="noreferrer">some spacing and emboldening are inconsistent</a>. See the SQL Server 2005 Surface Area Configuration tool for an example of inconsistent rendering.</p>\n'}, {'answer_id': 72720, 'author': 'Judah Gabriel Himango', 'author_id': 536, 'author_profile': 'https://Stackoverflow.com/users/536', 'pm_score': 2, 'selected': False, 'text': "<p>Creating a C++/CLI interop class to do the drawing in native code will result in crazy-fast drawing. We've witnesses this and measured it.</p>\n\n<p>If you're not up to doing that, we've found graphics.DrawString is just slightly faster than than TextRenderer.DrawText.</p>\n"}, {'answer_id': 4513455, 'author': 'fritz', 'author_id': 493388, 'author_profile': 'https://Stackoverflow.com/users/493388', 'pm_score': 2, 'selected': False, 'text': '<p>On my Windows 7 64 Bit system TextOut is even a bit slower than DrawString! TextRenderer.DrawText is much slower than DrawString.</p>\n'}, {'answer_id': 64655977, 'author': 'Chungalin', 'author_id': 2989229, 'author_profile': 'https://Stackoverflow.com/users/2989229', 'pm_score': 0, 'selected': False, 'text': '<p>From recent experience, fastest text output is achieved via <code>ExtTextOut</code> with <code>ETO_GLYPH_INDEX</code> flag. This comes at a price, and it’s that you aren’t printing characters anymore, but font glyphs directly. This means that you need to translate your regular character strings to glyph indexes strings prior calling <code>ExtTextOut</code>, either by calling <code>GetCharacterPlacement</code> everytime, or calling this function just once to build your own translation table, that will be valid until a new font is selected in the DC. Remember that glyph indexes are 16bit, so you can store them in a Unicode string and call <code>ExtTextOutW</code> version regardless of original string character size.</p>\n'}]
['https://Stackoverflow.com/questions/71374', 'https://Stackoverflow.com', 'https://Stackoverflow.com/users/6996/']