你理解错了msdn的话了,WM_PAINT会发送的条件不是“客户去不为空”,而是失效区域不为空!
这个区域就是你标记的或者是Winodws标记为失效的区域,失效的意思是这个区域内的内容已经不正确了,取消重新绘制。
你如何设置失效区域:调用InvalidateRect,另外,如果你要设置整个客户区都失效:
InvalidateRect(hWnd, NULL, TRUE); 不必调用GetClientRect。
何时Windows会自动设置失效区域?比如,你的窗口被其他窗口遮挡,如果此时用户把你的程序激活到前台,Windows自动设置刚才遮挡的部分为失效区域。以便在随后的WM_PAINT的时候这个区域会擦除之前的内容(之前的内容其实是另一个窗口的内容),画上自己窗口的内容。如果你的程序从最小化还原,整个客户去都会被Windows自动设置为失效区域。不过,鼠标滑过窗孔不会导致Windows自动设置失效区域,鼠标滑过在Windows中有特别处理,不需要程序员自己来操心。
只有当这个失效区域不为空的时候WM_PAINT才会被发送!而函数UpdateWindow的实质就是发送WM_PAINT,因而你如果不指定InvalidateRect则通过UpdateWindow不会更新窗口(确切的说是不一定会更新窗口,取决于Windows是否为你自动设置了失效区域)。
另外,Windows出于程序运行效率的考虑,在画图的时候,只有在失效区域的内容会被更新到屏幕上,如果你画了一个物体,在失效区域以外,那么这些语句直接会被Windows忽略。所以,正确设置失效区域是相当重要的,比如你写一个程序,有一个正方形,一个圆形,如果你这时候改变正方形的颜色,只要把这个正方形设置为失效区域即可。虽然你在响应WM_PAINT的时候同时也画了这个圆形,但是圆形由于不再失效区域,这些代码对Windows来说就相当于走了个过场,实际上没有操作显存。简单的程序,你偷懒直接设置全部客户去失效是可行的,但是如果你的WM_PAINT响应非常复杂,那么你不合理设置失效区域会导致程序界面闪烁,响应缓慢等问题。