DirectX5.0最新遊戲程式設計指南 DirectDraw教程篇 三、建立動畫 (轉)

worldblog發表於2007-12-04
DirectX5.0最新遊戲程式設計指南 DirectDraw教程篇 三、建立動畫 (轉)[@more@]

三、建立動畫
  上面的例子都只是將資料寫入後臺緩衝區,然後將後臺緩衝區與主表面翻轉,其速度並不太快。下面的例子DDEX4和DDEX5了實時功能,使看起來更象一個真正的遊戲。DDEX4顯示了怎樣為表面設定 Color key,怎樣使用IDirectDrawSurface::BltFast方法將屏外表面各部分複製到後臺緩衝區以產生動畫。DDEX5加入了讀取調色盤並在動畫執行時改變調色盤的功能。

1、Color Key和點陣圖動畫
  在DDEX3例中描述了將點陣圖放入屏外緩衝區的一種主要方式。DDEX4則使用了將背景和一系列的精靈(sprite,本例中精靈是圓環)裝入屏外表面的技術,然後使用, IDirectDrawSurface::BltFast方法將屏外表面的各部分複製到後臺緩衝區。doInit除了具有前面例子中的功能外,還包括了為精靈設定Color key的程式碼。Color key是用於設定透明度的顏色值。當使用塊寫方式時,矩型區域內除了設為 color key
的畫素,其它的畫素都被塊寫,由此在表面上產生非矩型的精靈。設定color key的程式碼如下:
  // Set the color key for this bitmap (black)
   // NOTE this bitmap has black as entry 255 in the color table.
 //  ddck.dwColorSpaceLowValue = 0xff;
 //  ddck.dwColorSpaceHighValue = 0xff;
 //  lpDDSOne->SetColorKey( DDCKEY_SRCBLT, &ddck );
  // if we did not want to hard code the palette index (0xff)
  // we can also set the color key like so...
   DDSetColorKey(lpDDSOne, RGB(0,0,0));
  return TRUE;
  例中給出了設定color key的兩種不同方法。第一種方法是註釋內的3行,先設定DDCOLORKEY 結構中color key的範圍,再IDirectDrawSurface::SetColorKey方法將color key 設定成黑色(假定點陣圖在顏色表中以黑色作為調色盤項255)。第二種方法是呼叫DDSetColorKey 函式設定顏色的RGB值來選擇color key,黑色就是RGB(0,0,0)。DDSetColorKey 函式呼叫了DDColorMatch函式,DDColorMatch 放置於lpDDSOne表面的點陣圖的0,0位置畫素的顏色值,然後用提供的RGB值賦給0,0位置的畫素,並將該顏色值遮蔽。
完成了這一步驟後,原來的顏色就可重新放回0,0處並用正確的Color Key呼叫DDSetColorKey函式,呼叫成功後,color key就放入 DDCOLORKEY 結構中的成員變數dwColorSpaceLowValue ,同時也複製到dwColorSpaceHighValue成員,然後再呼叫IDirectDrawSurface::SetColorKey 設定Color key。
  CLR_INVALID是DDSetColorKey 和DDColorMatch函式中另一個有用的變數。如果在 DDSetColorKey中以該值作為color key,點陣圖左上角的畫素就會作為color key使用。要想實現這一功能,需要調入點陣圖All.bmp,將0,0處的畫素值該為黑色,儲存更改,然後如下改變對DDSetColorKey 的呼叫:
 DDSetColorKey(lpDDSOne, CLR_INVALID);
重新編譯DDEX4,DDEX4就會使用0,0處的畫素值作為color key了。

2、DDEX4中的動畫
  DDEX4利用All.bmp中的紅色圓環呼叫updateFrame 函式來建立一個簡單的動畫。動畫由圓環的3各位置組成。例子透過比較中的GetTickCount和上次該函式開始執行的時間來判斷是否重畫哪個圓環,然後使用IDirectDrawSurface::BltFast方法將背景從屏外表面lpDDSOne位塊傳輸到後臺緩衝區,然後再使用已經設定好的color key將圓環塊寫入後臺緩衝區。在所有的圓環都塊寫到後臺緩衝區後,呼叫IDirectDrawSurface::Flip方法翻轉後臺緩衝區和主表面。

3、動態改變調色盤
  DDEX5描述了任何在執行時動態地改變調色盤,儘管在遊戲中這並不總是用到。DirectDraw確實能很好地控制調色盤。DDEX5中的下述程式碼將All.bmp檔案的下半部分中的調色盤裝入:
 // First, set all colors as unused
 for(i=0; i<256; i++) 
 {
  torulors[i] = 0;
 }
 // lock the surface and scan the lower part (the torus area)
 // and remember all the index's we find.
 ddsd.dwSize = sizeof(ddsd);
 while (lpDDSOne->Lock(NULL, &ddsd, 0, NULL) == DDERR_WASSTILLDRAWING);
 // Now search through the torus frames and mark used colors
 for( y=480; y<480+384; y++ ){
  for( x=0; x<640; x++ ) 
  {
  torusColors[((BYTE *)ddsd.lpSurface)[y*ddsd.lPitch+x]] = 1;
  }
  }
 lpDDSOne->Unlock(NULL);
  陣列torusColors用於指定All.bmp中的下半部分調色盤的索引值,陣列在使用之前都初始化為0。然後鎖定屏外表面來檢測某顏色索引值是否已用。陣列torusColors開始於點陣圖的第0行第480列,陣列中的顏色索引值由點陣圖表面 放置於的位置的一個位元組決定,該位置由DDSURFACEDESC 結構中的lpSurface成員變數來決定,lpSurface 指向對應於點陣圖(0,480)處的記憶體地址(y*lPitch+x)。陣列中設定的顏色索引值用來檢測調色盤中哪些顏色被替換。因為背景和紅色圓環之間沒有公用的顏色,所以只有那些同圓環聯在一起的顏色值才會被替換。

4、替換調色盤
  DDEX5中的updateFrame函式同DDEX4中的基本相同,先將背景塊寫入後臺緩衝區,再將3個紅色圓環塊寫到前景。但在翻轉表面之前,updateFrame用doInit函式建立的調色盤索引值來改變主表面的調色盤,程式碼如下:
 // Change the palette
 if(lpDDPal->GetEntries( 0, 0, 256, pe ) != DD_OK) {
  return;
 }
 for(i=1; i<256; i++){
  if(!torusColors[i])  {
  continue;
  }
  pe[i].peRed = (pe[i].peRed+2) % 256;
  pe[i].peGreen = (pe[i].peGreen+1) % 256;
  pe[i].peBlue = (pe[i].peBlue+3) % 256;
 }
 if(lpDDPal->SetEntries( 0, 0, 256, pe) != DD_OK){
  return;
 }
  IDirectDrawPalette::GetEntries方法在DirectDrawPalette中查詢調色盤的值,因為 pe指向的調色盤實體的值有效,方法就返回DD_OK,程式繼續執行。然後迴圈檢測torusColors在初始化中是否被設為1,如果索引值被設為1,由pe指向的調色盤的紅色、綠色、藍色的值就被替換。在所有的被標記的調色盤實體替換完畢後,再呼叫IDirectDrawPalette::SetEntries方法來真正改變DirectDrawPalette 中的實體。如果該調色盤已經設給主表面,上面的改變就會立即完成。完成了這一工作,剩下的就是同前面一樣的翻轉表面了。


來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/10752043/viewspace-987901/,如需轉載,請註明出處,否則將追究法律責任。

相關文章