天天看點

vc學習,Invalidate(true),Invalidate(false)

在學一個位圖顯示程式時,發現了圖像顯示能不能重繪的問題,當時看了msdn,也在網上看了不少回複。總感覺不是很了解。後來仔細試了一下,有點心得,特寫出來,以鼓勵自己。順便也為那些和我一樣剛開始學習vc的人提供些許幫助。

程式很簡單,如下:在文檔類中定義變量

下面是我在Doc類下面的變量:::

BITMAPFILEHEADER   bf;

BITMAPINFOHEADER   bi;

RGBQUAD*   quad;

BYTE*   lpBuf;

BITMAPINFO*pbi;

int   flag;

int   numQuad; 

在Doc類下面添加了指令處理函數打開檔案:

void   CMySeeView::OnFileOpen()  

{

//   TODO:   Add   your   command   handler   code   here

LPCTSTR   lpszFilter= "BMPFiles(*.bmp)|*.bmp ";

CFileDialog   dlg1(TRUE,lpszFilter,NULL,OFN_HIDEREADONLY|OFN_OVERWRITEPROMPT,lpszFilter,NULL);

CString   filename;

CFile   file;

if(dlg1.DoModal()==IDOK)

{

filename=dlg1.GetPathName();

if(file.Open(filename,CFile::modeRead|CFile::shareDenyNone,NULL)==1)

{

file.Read(&bf,sizeof(bf));

}

file.Read(&bi,sizeof(bi));

numQuad=0;

if(bi.biBitCount <24)

{

numQuad=1 < <bi.biBitCount;

}

pbi=(BITMAPINFO*)HeapAlloc(GetProcessHeap(),0,sizeof(BITMAPINFOHEADER)+numQuad*sizeof(RGBQUAD));

memcpy(pbi,&bi,sizeof(bi));

quad=(RGBQUAD*)((BYTE*)pbi+sizeof(BITMAPINFOHEADER));

file.Read(quad,sizeof(RGBQUAD)*numQuad);

bi.biSizeImage=bf.bfSize-bf.bfOffBits;

lpBuf=(BYTE*)HeapAlloc(GetProcessHeap(),0,bi.biSizeImage);

file.Read(lpBuf,bi.biSizeImage);

file.Close();

}

flag==1

}

然後繪圖:畫圖::

void   CMySeeView::OnDraw(CDC*   pDC)

{

 CMySeeDoc* pDoc = GetDocument();

 ASSERT_VALID(pDoc);

  if(pDoc->flag==1)

 {

  SetDIBitsToDevice(pDC->m_hDC,0,0,pDoc->bi.biWidth,pDoc->bi.biHeight,0,0,0,pDoc->bi.biHeight,pDoc->lpBuf,pDoc->pbi,DIB_RGB_COLORS);

 }

Invalidate(false);/這個地方用Invalidate(true)和不用的情況下出現的結果寫在下面。

}

現象如下:

(1)Invalidate(false)正常   (2)Invalidate(true)出現刷屏      (3)如果不用,那麼每次打開檔案将不能自動顯示,可以手動更改視窗大小,那麼就可以正常顯示了。

分析如下:當參數為false時,客戶區無效,引起重繪,但不擦除背景,是以我們可以看到我們的圖像。當參數為true時,也引起重繪,我們可以看到自己的圖像,但由于擦除背景以後才發生重繪,是以看到刷屏的現象。而不用的話就會一直顯示背景,除非認為改變視窗或其他方式引發視窗重繪,顯示圖像。