Как устранить мерцание при стирании фона в mfc
Я работаю с приложением SDI, чтобы перерисовать график и обновить данные с помощью таймера в View file. Хотя я использую ON_WM_ERASEBKGND для устранения мерцания, но это все же происходит. И ниже мой код, который я пытался реализовать. У кого-нибудь есть идеи по устранению мерцания?
Вот мой MSG_MAP
ON_WM_PAINT()
ON_WM_ERASEBKGND()
ON_WM_TIMER()
BOOL CVCDSOView::OnEraseBkgnd(CDC* pDC)
{
// TODO: Add your message handler code here and/or call default
return TRUE;
return CView::OnEraseBkgnd(pDC);
}
void CVCDSOView::OnInitialUpdate()
{
CView::OnInitialUpdate();
CRect Rect;
GetClientRect(&Rect);
CRect m_rcDraw = Rect;
// set timer with 200ms
SetTimer(ID_LABEL_COMPANY,200,NULL);
labelCompany.Create(_T("Company"), WS_CHILD | WS_VISIBLE,
CRect(LEFT_SIDE, TOP_SIDE, RIGHT_SIDE+50, BOTTOM_SIDE), this, ID_LABEL_COMPANY);
textboxCompany.Create(WS_CHILD | WS_VISIBLE | WS_TABSTOP | WS_BORDER | ES_NOHIDESEL,
CRect(LEFT_SIDE, TOP_SIDE+VERTICAL_OFFSET, RIGHT_SIDE+50, BOTTOM_SIDE+VERTICAL_OFFSET), this, ID_EDITTEXT_COMPANY);
}
// CVCDSOView message handlers
void CVCDSOView::OnPaint()
{
CPaintDC dc(this); // device context for painting
// TODO: Add your message handler code here
CRect Rect;
GetClientRect(&Rect);
CDC dcMem;
CBitmap bmpMem;
dcMem.CreateCompatibleDC(&dc);
bmpMem.CreateCompatibleBitmap(&dc,Rect.Width()- GRID_LEFT,Rect.Height()-35);
dcMem.SelectObject(&bmpMem);
dcMem.FillSolidRect(Rect, RGB(255,255,255));
CRect m_rcDraw = Rect;
m_rcDraw.DeflateRect(GRID_LEFT,GRID_TOP,GRID_RIGHT,GRID_BOTTOM);
DrawGrid(&dcMem,m_rcDraw);
dc.BitBlt(0,0,Rect.Width(),Rect.Height(),&dcMem,0,0,SRCCOPY);
dcMem.DeleteDC();
DeleteObject(bmpMem);
// Do not call CView::OnPaint() for painting messages
}
void CVCDSOView::OnTimer(UINT nIDEvent)
{
// TODO: Add your message handler code here and/or call default
//
if(nIDEvent==ID_LABEL_COMPANY)
{
CollectData();
Invalidate();
CView::OnTimer(nIDEvent);
}
}
Любая идея была бы очень признательна.
2 ответа
У вас есть дочерние элементы управления, которые могут вызвать мерцание, когда их фон окрашен. Вы хотите исключить дочерние элементы управления из области рисования, добавив WS_CLIPCHILDREN
Отметить класс просмотра:
BOOL CVCDSOView::PreCreateWindow(CREATESTRUCT& cs)
{
cs.style |= WS_CLIPCHILDREN;
return CView::PreCreateWindow(cs);
}
Не связано с мерцающей проблемой:
Не вычитайте ничего для основного прямоугольника. Вы должны изменить растровое изображение на
bmpMem.CreateCompatibleBitmap(&dc, Rect.Width(), Rect.Height());
Вам не нужно dcMem.DeleteDC()
а также DeleteObject(bmpMem)
MFC автоматически удалит эти объекты.
Обратите внимание, что MFC не будет автоматически отменять выбор объектов. Это обычно не имеет значения, потому что Windows выполнит необходимую очистку, как в этом примере. Но для полноты картины добавьте следующее:
CBitmap* oldbitmap = (CBitmap*)dcMem.SelectObject(&bmpMem);
...
dc.BitBlt(0,0,Rect.Width(),Rect.Height(),&dcMem,0,0,SRCCOPY);
dcMem.SelectObject(oldbitmap);
- В
OnEraseBkgnd
ты должен вернутьсяFALSE
, Все рисование в
OnPaint
лучше сделать сCMemDC
класс, потому что рисование прямо на экране, скорее всего, также вызовет мерцание:CMemDC memDC(*pDC, this); CDC& rDC = memDC.GetDC(); rDC.ActualDrawing`...