{"id":18623,"date":"2009-04-06T07:00:00","date_gmt":"2009-04-06T07:00:00","guid":{"rendered":"https:\/\/blogs.msdn.microsoft.com\/oldnewthing\/2009\/04\/06\/theres-nothing-wrong-with-making-bold-treeview-items\/"},"modified":"2009-04-06T07:00:00","modified_gmt":"2009-04-06T07:00:00","slug":"theres-nothing-wrong-with-making-bold-treeview-items","status":"publish","type":"post","link":"https:\/\/devblogs.microsoft.com\/oldnewthing\/20090406-00\/?p=18623","title":{"rendered":"There&#8217;s nothing wrong with making bold treeview items"},"content":{"rendered":"<p><P>\nCommenter Frans Bouma asks,\n<\/P>\n<BLOCKQUOTE CLASS=\"q\">\n<A HREF=\"http:\/\/blogs.msdn.com\/oldnewthing\/pages\/407234.aspx#549386\">\nWhy is the text of a treenode chopped off\nwhen you switch the font from normal to bold<\/A>?\n<a href=\"http:\/\/groups.google.com\/group\/microsoft.public.dotnet.languages.csharp\/browse_frm\/thread\/79297a46ef22f520\/a51c76da39b1437a\">\nIt apparently is for backwards compatibility<\/A>\nbut I fail to see why this is necessary for backward compatibility&#8230;\n<\/BLOCKQUOTE>\n<P>\nActually, bold treeview items work just fine.\nWatch:\n<\/P>\n<P>\nStart with our \n<A HREF=\"http:\/\/blogs.msdn.com\/oldnewthing\/archive\/2003\/07\/23\/54576.aspx\">\nscratch program<\/A>\nand make these changes:\n<\/P>\n<PRE>\nBOOL\nOnCreate(HWND hwnd, LPCREATESTRUCT lpcs)\n{\n  <FONT COLOR=\"blue\">g_hwndChild = CreateWindow(\n      WC_TREEVIEW, NULL, WS_CHILD | WS_VISIBLE | WS_TABSTOP |\n      TVS_HASBUTTONS | TVS_HASLINES | TVS_LINESATROOT,\n      0, 0, 0, 0, hwnd, (HMENU)1, g_hinst, 0);<\/p>\n<p>  TVINSERTSTRUCT tvis;\n  tvis.hParent = TVI_ROOT;\n  tvis.hInsertAfter = TVI_LAST;\n  tvis.item.mask = TVIF_TEXT | TVIF_STATE;\n  tvis.item.stateMask = TVIS_BOLD;\n  tvis.item.state = 0;\n  tvis.item.pszText = TEXT(&#8220;First&#8221;);<\/p>\n<p>  tvis.hParent = TreeView_InsertItem(g_hwndChild, &amp;tvis);<\/p>\n<p>  tvis.item.pszText = TEXT(&#8220;Second&#8221;);\n  tvis.item.state = TVIS_BOLD;\n  TreeView_InsertItem(g_hwndChild, &amp;tvis);<\/p>\n<p>  tvis.item.pszText = TEXT(&#8220;Third&#8221;);\n  tvis.item.state = 0;\n  TreeView_InsertItem(g_hwndChild, &amp;tvis);<\/FONT><\/p>\n<p>  return TRUE;\n}\n<\/PRE>\n<P>\nI elided error checking for expository purposes.\n<\/P>\n<P>\nThis code creates a tree view and populates it as follows:\n<\/P>\n<UL>\n<LI>First\n<UL>\n<LI><B>Second<\/B>\n<LI>Third\n<\/UL>\n<\/UL>\n<P>\nWhen you run this program, you can see that the text for all\nthe items appears as expected; nothing is truncated.\n<\/P>\n<P>\nAs for the backward compability remark,\nit&#8217;s quite simple:\n<I>Every change, no matter how seemingly insignificant,\nhas compatibility consequences<\/I>.\nThe common controls are heavily used in third party programs,\nmany of which make strange assumptions about how the controls work,\nrelying on quirks of implementations in strange ways.\nFor example,\nthose who have read\n<A HREF=\"http:\/\/www.awprofessional.com\/title\/0321440307\">\nthe first bonus chapter of my book<\/A>\nwill know that even something as seemingly harmless as\nfixing a flicker bug in the status bar resulted in\na broken status bar in a program from a major software publisher.\nEvery change is taken with great trepidation, and the bias is\nto preserve bug-for-bug compatibility.\n<\/P>\n<P>\nIn this case, the issue was with the way the width of the treeview\nitem is calculated.\nYou can easily imagine programs which worked around the existing behavior\nby artificially padding the item with spaces to compensate for\nthe miscalculation.\nIf the treeview suddenly fixed the bug,\nthese treeview items would now be undesirably large,\npossibly creating a horizontal scroll bar where there previously\nhad been none, resulting in \nbugs like &#8220;After upgrading, the last item in my treeview is\nbeing covered by a scroll bar.&#8221;\nWe saw something like this before when we looked at\n<A HREF=\"http:\/\/blogs.msdn.com\/oldnewthing\/archive\/2005\/02\/08\/369090.aspx\">\nthe effects of the <CODE>DS_SHELLFONT<\/CODE> dialog style<\/A>:\nFixing the bug described in that article would result in property\nsheet pages coming out undesirably large (because their sizes were\nartificially inflated to compensate for the erroneous calculation).\n<\/P>\n<P>\nThat doesn&#8217;t mean the bug can&#8217;t get fixed, however.\nJust as the <CODE>DS_SHELLFONT<\/CODE> flag is a signal to say\nthat your property sheet page wants to use the new calculations,\nyou can tell the tree view\n&#8220;Please give me the version of the treeview that fixes the\nfont bug&#8221; by sending it the <CODE>CCM_SETVERSION<\/CODE> message\nand specifying that you want version&nbsp;5.\nSimilarly, you can opt into version&nbsp;6 of the common controls\nby providing a manifest.\n<\/P>\n<P>\n<B>Update<\/B>:\nI slipped a subtlety into this article which\n<A HREF=\"http:\/\/blogs.msdn.com\/oldnewthing\/archive\/2009\/04\/06\/9532674.aspx#9533858\">\nit appears people didn&#8217;t pick up on<\/A>,\nso I&#8217;ll make it explicit.\n<\/P>\n<P>\nThe original question was about &#8220;switching the font from normal to bold&#8221;,\nbut there are multiple ways of doing this.\nMy sample code used the recommended (declarative) method of setting the\n<CODE>TVIS_BOLD<\/CODE> flag.\nBut if you click through the link, you&#8217;ll see that\nthe original commenter was using the procedural method of\nhandling the <CODE>NM_CUSTOMDRAW<\/CODE> notification,\nselecting a new font\n(a boldface variation of the normal font),\nand returning <CODE>CRF_NEWFONT<\/CODE>.\nThis is a technique I had illustrated previously with\n<A HREF=\"http:\/\/blogs.msdn.com\/oldnewthing\/archive\/2005\/09\/16\/468800.aspx\">\nlist views<\/A>\nand\n<A HREF=\"http:\/\/blogs.msdn.com\/oldnewthing\/archive\/2006\/06\/27\/648493.aspx\">\ntool tips<\/A>.\n<\/P>\n<P>\nThe compatibility behavior is for fonts customized via\n<CODE>NM_CUSTOMDRAW<\/CODE>.\nThe declarative method was added specifically to address the bug\nin item size calculations when people change the font procedurally:\nOlder versions of the treeview control asked for the custom font\nonly when painting; it didn&#8217;t ask for the custom font when measuring.\nAdding the font query to version&nbsp;6 was actually quite risky,\nsince the only way to ask the application for the procedurally-applied\nfont is to <I>actually go through the motions of drawing it<\/I>,\ngenerating a\n<A HREF=\"http:\/\/blogs.msdn.com\/oldnewthing\/archive\/2006\/03\/27\/561924.aspx\">\ndummy <CODE>NM_CUSTOMDRAW<\/CODE> notification\nwith an empty paint rectangle<\/A>.\nIf an application painted outside the rectangle, you would have seen\nseen random painting on the screen.\n<\/P><\/p>\n","protected":false},"excerpt":{"rendered":"<p>Commenter Frans Bouma asks, Why is the text of a treenode chopped off when you switch the font from normal to bold? It apparently is for backwards compatibility but I fail to see why this is necessary for backward compatibility&#8230; Actually, bold treeview items work just fine. Watch: Start with our scratch program and make [&hellip;]<\/p>\n","protected":false},"author":1069,"featured_media":111744,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"footnotes":""},"categories":[1],"tags":[25],"class_list":["post-18623","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-oldnewthing","tag-code"],"acf":[],"blog_post_summary":"<p>Commenter Frans Bouma asks, Why is the text of a treenode chopped off when you switch the font from normal to bold? It apparently is for backwards compatibility but I fail to see why this is necessary for backward compatibility&#8230; Actually, bold treeview items work just fine. Watch: Start with our scratch program and make [&hellip;]<\/p>\n","_links":{"self":[{"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/posts\/18623","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/users\/1069"}],"replies":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/comments?post=18623"}],"version-history":[{"count":0,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/posts\/18623\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/media\/111744"}],"wp:attachment":[{"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/media?parent=18623"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/categories?post=18623"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/tags?post=18623"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}