This problem occurs. In onerasebkgnd, if you do not call the default
The onerasebkgnd of is only a re-painting background, and will not flash. In onpaint,
Because it implicitly calls onerasebkgnd, and you have not processed onerasebkgnd
Function, which is related to the default background of the window.
The onerasebkgnd operation uses the Default background of the window to fl the new background (generally
And then you re-draw the background, causing the screen to flash.
Another problem is that onerasebkgnd is not called every time. If you
If the parameter is true when invalidate is called, it is hidden in onpaint.
The wm_erasebkgnd message is generated when beginpaint is called. If the Parameter
If this parameter is set to false, the background will not be refreshed.
So there are three and a half solutions:
1. Use onerasebkgnd instead of calling the original onerasebkgnd function.
2. onpaint is used and onerasebkgnd is reloaded.
3. Use onpaint to set the background to blank when creating a window.
4. Use onpaint, but use invalidate (false) for Refresh.
(However, in this case, the refresh caused by window overwrite still needs to flash.
So it is not a thorough solution)
They are quite simple.
------------------------------------------------------
In MFC, the drawing of any window component is placed in the two member functions.
Onerasebkgnd () is used to draw the basemap, while onpaint () is used to draw the main object.
For example, there is text on the gray button.
What onerasebkgnd () does is to gray the button.
What onpaint () does is to draw text.
Since both member functions are used to draw Components
So why should we separate onpaint () and onerasebkgnd ()?
In fact, the onpaint () and onerasebkgnd () features are different.
1. The requirement of onerasebkgnd () is to quickly plot the program in it, preferably not to consume too much time.
Because onerasebkgnd () will be called immediately whenever there is any small change to the window component ()
2. onpaint () is called only when the program is idle.
3. onerasebkgnd () is called before onpaint ()
Therefore, onpaint () may call onerasebkgnd () several times before being called.
If we are a person who is working on graphical user interfaces
We usually need to set a beautiful image as the basemap of our dialog.
Putting the drawing program code in onpaint () may often encounter some problems.
For example, drag a window and move it on the dialog.
The dialog changes to gray until the action stops.
This is because the program calls onerasebkgnd () immediately every time it needs to be re-painted ()
Onerasebkgnd () draws the dialog into gray.
The program will call onpaint () only after the action is stopped. Then the basemap we want to draw will be pasted.
The solution to this problem is to rewrite onerasebkgnd () to a function that does not work.
As shown below
Bool cmydlg: onerasebkgnd (CDC * PDC)
{
Return true;
}
The above will call cdialog: onerasebkgnd (), but if we do not call
The program won't have a gray background.
It is better to directly move the plotting program from onpaint () to onerasebkgnd ().
As shown below
// M_bmp bkgnd is a cbitmap object and our basemap has been loaded before.
// The size of the basemap is the same as that of the client.
Bool cmydlg: onerasebkgnd (CDC * PDC)
{
Crect RC;
Getupdaterect (& rc );
CDC srcdc;
Srcdc. createcompatibledc (PDC );
Srcdc. SelectObject (m_bmp bkgnd );
PDC-> bitblt (RC. Left, RC. Top, RC. getwidth (),
RC. getheight (), & srcdc, RC. Left, RC. Top, srccopy );
Return true;
}
Note that getupdaterect () instead of getclientrect () is used to obtain the redraw size ()
If getclientrect () is used, it will redraw the areas where the image should not be repainted.
In addition, getupdaterect () is not recommended. In many cases, this function may be called in onerasebkgnd. getclipbox () is recommended ()
First of all, tr0j4n is a good man and has been written so long. But it seems wrong.
This should be the case. When Windows determines that the customer zone needs to be re-painted, it first sends the wm_erasebkgnd message to the window process. By default, the wm_erasebkgnd message is processed and the background is refreshed with a white image, then, the wm_paint message is sent to the window. The response program of the wm_paint message is responsible for painting the content of the customer area. In other words, when Windows determines that the customer zone needs to be re-painted, it sends the wm_erasebkgnd and wm_paint messages respectively, and the response programs of these two messages are responsible for flushing the background and re-painting the customer content respectively.
The problem is that, after the background is removed, Windows has output the video card cache to the screen before wm_paint is completed.
How do I erase the previous background image?
I understand the problem. Your problem is that when the window size changes, the original background is not cleared, causing overlapping display of images. The code above is correct and is written in onerasebkgnd () the results written in onpaint () are the same. The main reason is that when we change the window size, the wm_size message is triggered, the default onsize parameter used when calling invalidate internally is: invalidate (flase); that is, the background is not refreshed. Therefore, the original background cannot be flushed.
The solution is to process wm_size. In onsize (), call: invalidate (true); force refresh the background.