{"id":43483,"date":"2014-12-03T07:00:00","date_gmt":"2014-12-03T07:00:00","guid":{"rendered":"https:\/\/blogs.msdn.microsoft.com\/oldnewthing\/2014\/12\/03\/what-happens-if-i-dont-paint-when-i-get-a-wm_paint-message\/"},"modified":"2014-12-03T07:00:00","modified_gmt":"2014-12-03T07:00:00","slug":"what-happens-if-i-dont-paint-when-i-get-a-wm_paint-message","status":"publish","type":"post","link":"https:\/\/devblogs.microsoft.com\/oldnewthing\/20141203-00\/?p=43483","title":{"rendered":"What happens if I don&#039;t paint when I get a WM_PAINT message?"},"content":{"rendered":"<p>\nSuppose your window procedure doesn&#8217;t paint when it gets a\n<code>WM_PAINT<\/code> message.\nWhat happens?\n<\/p>\n<p>\nIt depends on how you don&#8217;t paint.\n<\/p>\n<p>\nIf you have an explicit handler for the\n<code>WM_PAINT<\/code> message\nthat does nothing but return without painting,\nthen the window manager will turn around and\nput a new\n<code>WM_PAINT<\/code> message in your queue.\n&#8220;And try harder this time.&#8221;\nRemember that the rules for the\n<code>WM_PAINT<\/code> message are that the window manager will\ngenerate a\n<code>WM_PAINT<\/code> message\nfor any window that has a dirty region.\nIf you fail to remove the dirty region in your\n<code>WM_PAINT<\/code> message handler,\nwell, then the rules state that you get another\n<code>WM_PAINT<\/code> message.\n(The most common way of clearing the dirty region is to call\n<code>Begin&shy;Paint<\/code>,\nbut there are other less common ways,\nlike\n<code>Validate&shy;Rect<\/code> or\n<code>Redraw&shy;Window<\/code> with the <code>RDW_VALIDATE<\/code> flag.)\n<\/p>\n<p>\nThe other case is that you\nsimply don&#8217;t have a <code>WM_PAINT<\/code> handler\nand let the message fall through to\n<code>Def&shy;Window&shy;Proc<\/code>.\nIn that case,\n<code>Def&shy;Window&shy;Proc<\/code>\nwill do a blank paint for you.\nIn other words,\n<code>Def&shy;Window&shy;Proc<\/code> contains\nthe logical equivalent of\n<\/p>\n<pre>\ncase WM_PAINT:\n {\n  PAINTSTRUCT ps;\n  if (BeginPaint(hwnd, &amp;ps))\n   EndPaint(hwnd, &amp;ps);\n }\n return 0;\n<\/pre>\n<p>\nIn the case where you pass the\n<code>WM_PAINT<\/code> to\n<code>Def&shy;Window&shy;Proc<\/code>,\nthe dirty region is cleared because\n<code>Def&shy;Window&shy;Proc<\/code>\nwill call\n<code>Begin&shy;Paint<\/code> for you.\n<\/p>\n<p>\nThere are some quirks in the handling of the\n<code>WM_PAINT<\/code> message by the\n<code>Def&shy;Window&shy;Proc<\/code> function\nto handle various application compatibility cases,\nbut the above is the basic idea.\n<\/p>\n<p>\nTo avoid tripping over the weird application compatibility\ncases, decide up front how you want to deal with\n<code>WM_PAINT<\/code> messages delivered to your window\nprocedure.\n<\/p>\n<ul>\n<li>Handle them completely\n    by calling\n    <code>Begin&shy;Paint<\/code> and\n    <code>End&shy;Paint<\/code>,\n    then returning 0.\n    (Do not pass the message to\n    <code>Def&shy;Window&shy;Proc<\/code>.)<\/p>\n<li>Pass them all to\n    <code>Def&shy;Window&shy;Proc<\/code>,\n    and let it do the\n    <code>Begin&shy;Paint<\/code> and\n    <code>End&shy;Paint<\/code>.\n<\/ul>\n<p>\nDon&#8217;t try playing fancy games like\n&#8220;Oh, I&#8217;m going to call\n<code>Begin&shy;Paint<\/code> and\n<code>End&shy;Paint<\/code>,\nbut sometimes I&#8217;m <i>also<\/i> going to pass the message to\n<code>Def&shy;Window&shy;Proc<\/code> afterwards.&#8221;\nJust pick one plan and stick to it.\nIt&#8217;s a lot simpler for everybody that way.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Suppose your window procedure doesn&#8217;t paint when it gets a WM_PAINT message. What happens? It depends on how you don&#8217;t paint. If you have an explicit handler for the WM_PAINT message that does nothing but return without painting, then the window manager will turn around and put a new WM_PAINT message in your queue. &#8220;And [&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-43483","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-oldnewthing","tag-code"],"acf":[],"blog_post_summary":"<p>Suppose your window procedure doesn&#8217;t paint when it gets a WM_PAINT message. What happens? It depends on how you don&#8217;t paint. If you have an explicit handler for the WM_PAINT message that does nothing but return without painting, then the window manager will turn around and put a new WM_PAINT message in your queue. &#8220;And [&hellip;]<\/p>\n","_links":{"self":[{"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/posts\/43483","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=43483"}],"version-history":[{"count":0,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/posts\/43483\/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=43483"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/categories?post=43483"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/oldnewthing\/wp-json\/wp\/v2\/tags?post=43483"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}