Visual C++中的圖形特技 (轉)
Visual C++中的圖形特技 (轉)[@more@]隨著資訊表示及實現的多化,在許多學習、遊戲軟體,以及多媒體課件製作軟體中,經常使用各種圖形顯示技巧,如圖形的推拉、交錯、雨滴狀、百頁窗、積木隨機堆疊等顯示。這樣使畫面變得更為生動活潑,更能吸引,也為更好地發揮軟體的功能奠定了基礎。本文就Visual C++ 6.0中實現圖形的各種顯示技巧的原理及具體方法做些探討。
基本原理
在Visual C++6.0中,顯示點陣圖的方法及過程如下:
1. 顯示資源中的點陣圖(點陣圖的所有資料均存在於可中)
(1)從資源中裝入點陣圖
● 定義點陣圖資料成員CBitmap m_Bitmap;
● CBitmap成員Loaitmap(),如m_Bitmap.LoadBitmap(IDB_BITMAP1);
● 傳入LoadBitmap的引數是點陣圖在圖形編輯器中生成或從位件中引入時賦予的識別符。
(2)生成與點陣圖相聯絡的裝置情境物件
CDC MemDC;
MemDC.CreateCompatibleDC(NULL);
MemDC.(&m_Bitmap);
(3)顯示點陣圖
CClientDC ClientDC(this);
BITMAP BM;
m_Bitmap.GetObject(sizeof(BM),&BM);
ClientDC.BitBlt
( X,Y, //目標裝置邏輯橫、縱座標
BM.bmWidth, BM.bmHeight, //顯示點陣圖的畫素寬、高度
&MemDC,
//待顯示點陣圖資料的裝置情境物件
0,0, //源資料中的橫、縱座標
SRCCOPY); //位操作方式
這種方法顯示點陣圖速度快,但不是很靈活,而且會使可執行檔案增大。
2. 顯示獨立檔案方式的點陣圖(點陣圖的所有資料獨立於可執行檔案)
HBITMAP *hBitmap; //定義點陣圖物件控制程式碼
BITMAP BM;
CDC MemDC;
CClientDC ClientDC(this);
MemDC.CreateCompatibleDC(&ClientDC);
hBitmap=(HBITMAP*):: LoadImage
( AfxGetInstanceHandle(),
//取得應用程式控制程式碼
“demo1.bmp”,
//點陣圖檔名
IMAGE_BITMAP,
//型別為點陣圖
0,0,
LR_LOADFROMFILE);
//從檔案中取點陣圖資料
MemDC.SelectObject(hBitmap);
:: GetObject(hBitmap,sizeof(BM),&BM);
ClientDC.BitBlt(……)
//使用格式與方法一同
這種方法顯示點陣圖速度較之前一種慢了一點,但其靈活性較大,可以任意變換點陣圖檔案,而無需重新編譯源程式, 也減小了可執行檔案的大小。
實現方法
下面介紹各種圖形顯示技巧的具體實現原理及方法。以下所有程式演算法的實現均可放在視類(CView,也可視自己的需要放在其他類)中處理,且有必要進行如下的相關操作:
增加如下類成員變數:
BITMAP m_Bm;
//儲存點陣圖的寬、高度等資料
HBITMAP *m_hBitmap;
//儲存點陣圖資料控制程式碼
CDC m_MemDC; //記憶體裝置情境物件
在類建構函式中加入如下程式碼:
m_MemDC.CreateCompatibleDC(NULL); //產生記憶體裝置情境物件
m_hBitmap=(HBITMAP *)::LoadImage(
//從檔案中裝入點陣圖資料
AfxGetInstanceHandle(),
“demo1.bmp”,
IMAGE_BITMAP,
0,0,
LR_LOADFROMFILE );
m_MemDC.SelectObject(m_hBitmap); //將點陣圖選入記憶體裝置情境物件
::GetObject(m_hBitmap,sizeof(m_Bm),&m_Bm);
1. 水平交錯效果
原理:將記憶體裝置情境物件(如MemDC)中的點陣圖資料拆分成奇、偶掃描線兩部分,其中奇數條掃描線由上往下移動,偶數條掃描線則由下往上移動,且兩者同時進行。螢幕上的效果為分別由上下兩端出現的較淡柵欄圖形,逐漸相互靠近,直至整個點陣圖完全清楚。垂直交錯效果的實現原理與之類似。
程式演算法:
int i,j;
for ( i=0; i<=m_Bm.bmHeight; i+=2 )
{j = i;
while ( j>0 )
{ClientDC.StretchBlt(
//奇數,由上至下
0,j-1,
//目標裝置邏輯橫、縱座標
m_Bm.bmWidth,1,
//顯示點陣圖的畫素寬、高度
&m_MemDC,
//源點陣圖裝置情境物件
0,m_Bm.bmHeight-(i-j-1),
//源點陣圖的起始橫、縱座標
m_Bm.bmWidth,1,
//源點陣圖的畫素寬、高度
SRCCOPY);
ClientDC.StretchBlt(
//偶數,由下至上
0,m_Bm.bmHeight-j,
//目標裝置邏輯橫、縱座標
m_Bm.bmWidth,1,
//顯示點陣圖的畫素寬、高度
&m_MemDC,
//源點陣圖裝置情境物件
0,i-j,
//源點陣圖的起始橫、縱座標
m_Bm.bmWidth,1,
//源點陣圖的畫素寬、高度
SRCCOPY);
j-=2; }
// while ( j>0 )
Sleep(10);
}
//for ( i=0; i<=m_Bm.bmHeight; i+ =2 )
2. 雨滴效果
原理:將記憶體裝置情境物件(如MemDC)中點陣圖資料的最後一條掃描線,順序地從目標裝置(如ClientDC)中待顯示點陣圖的第一條掃描線所在位置移動至最後一條處,並保留此條掃描線在螢幕上移動時留下的軌跡。接著再把MemDC中點陣圖資料的倒數第二條掃描線,順序地從目標裝置(如ClientDC)中待顯示點陣圖的第一條掃描線所在位置移動至倒數第二條處。其餘的掃描線依此類推。
程式演算法:
int i,j;
for ( i=0; i<=m_Bm.bmHeight; i++ )
{for ( j=0; j<=m_Bm.bmHeight-i; j++ )
ClientDC.StretchBlt(
0,j,
//目標裝置邏輯橫、縱座標
m_Bm.bmWidth,1,
//顯示點陣圖的畫素寬、高度
&m_MemDC,
//源點陣圖裝置情境物件
0,m_Bm.bmHeight-i,
//源點陣圖的起始橫、縱座標
m_Bm.bmWidth,1,
//源點陣圖的畫素寬、高度
SRCCOPY);
Sleep(20);
}
//for ( i=0; i<=m_Bm.bmHeight; i++ )
3. 百葉窗效果
原理:將記憶體裝置情境物件(如MemDC)中的點陣圖資料分成若干組,然後分別從第一組到最後一組進行搬移,第一次搬移每組中第一條掃描線到目標裝置(如ClientDC)中待顯示點陣圖的相應位置,第二次搬移每組中第二條掃描線,接著第三條、第四條掃描線。
程式演算法:
int i,stepi,j;
stepi=m_Bm.bmHeight/10;
for ( i=0; i<=stepi; i++ )
{for ( j=0; j<10; j++ )
ClientDC.StretchBlt(
0,j*stepi+i,
//目標裝置邏輯橫、縱座標
m_Bm.bmWidth,1,
//顯示點陣圖的畫素寬、高度
&m_MemDC,
//源點陣圖裝置情境物件
0,j*stepi+i,
//源點陣圖的起始橫、縱座標
m_Bm.bmWidth,1,
//源點陣圖的畫素寬、高度
SRCCOPY);
Sleep(20);
} //for ( i=0; i<=stepi; i++ )
4. 隨機積木效果
原理:將記憶體裝置情境物件(如MemDC)中的點陣圖資料分成縱橫十等份共一百組資料,然後隨機地取出這一百組資料中的某一組顯示到目標裝置(如ClientDC)中待顯示點陣圖的相應位置,如此反覆直到所有一百組資料均顯示完畢為止。
程式演算法:
int i,j,stepx,stepy,dispnum,x,y;
int pxy[10][10];
//使用本陣列記錄已顯示過的資料組
for ( i=0; i<10; i++ )
for ( j=0; j<10; j++ )
pxy[i][j]=0;
stepx=m_Bm.bmWidth/10;
stepy=m_Bm.bmHeight/10;
srand( (unsigned)time( NULL ) );
dispnum=0;
//記錄已顯示過的資料組的個數
while(1)
{ x=rand() % 10;
y=rand() % 10;
if ( pxy[x][y] )
//本組x,y所代表的資料組是否已顯示過?
continue;
pxy[x][y]=1;
//表明本組x,y所代表的資料組已顯示過
ClientDC.StretchBlt(
x*stepx, y*stepy,
//目標裝置邏輯橫、縱座標
stepx,stepy,
//顯示點陣圖的畫素寬、高度
&m_MemDC,
//源點陣圖裝置情境物件
x*stepx, y*stepy,
//源點陣圖的起始橫、縱座標
stepx,stepy,
//源點陣圖的畫素寬、高度
SRCCOPY);
dispnum++;
if ( dispnum >=100 )
break;
Sleep(30);
} // while(1)
結 語
以上程式程式碼均在Visual C++ 6.0中透過,所有片斷均可編寫成獨立的函式,靈活使用。如果對以上幾種顯示效果進行變換,我們還可以實現多種其他特技效果。
基本原理
在Visual C++6.0中,顯示點陣圖的方法及過程如下:
1. 顯示資源中的點陣圖(點陣圖的所有資料均存在於可中)
(1)從資源中裝入點陣圖
● 定義點陣圖資料成員CBitmap m_Bitmap;
● CBitmap成員Loaitmap(),如m_Bitmap.LoadBitmap(IDB_BITMAP1);
● 傳入LoadBitmap的引數是點陣圖在圖形編輯器中生成或從位件中引入時賦予的識別符。
(2)生成與點陣圖相聯絡的裝置情境物件
CDC MemDC;
MemDC.CreateCompatibleDC(NULL);
MemDC.(&m_Bitmap);
(3)顯示點陣圖
CClientDC ClientDC(this);
BITMAP BM;
m_Bitmap.GetObject(sizeof(BM),&BM);
ClientDC.BitBlt
( X,Y, //目標裝置邏輯橫、縱座標
BM.bmWidth, BM.bmHeight, //顯示點陣圖的畫素寬、高度
&MemDC,
//待顯示點陣圖資料的裝置情境物件
0,0, //源資料中的橫、縱座標
SRCCOPY); //位操作方式
這種方法顯示點陣圖速度快,但不是很靈活,而且會使可執行檔案增大。
2. 顯示獨立檔案方式的點陣圖(點陣圖的所有資料獨立於可執行檔案)
HBITMAP *hBitmap; //定義點陣圖物件控制程式碼
BITMAP BM;
CDC MemDC;
CClientDC ClientDC(this);
MemDC.CreateCompatibleDC(&ClientDC);
hBitmap=(HBITMAP*):: LoadImage
( AfxGetInstanceHandle(),
//取得應用程式控制程式碼
“demo1.bmp”,
//點陣圖檔名
IMAGE_BITMAP,
//型別為點陣圖
0,0,
LR_LOADFROMFILE);
//從檔案中取點陣圖資料
MemDC.SelectObject(hBitmap);
:: GetObject(hBitmap,sizeof(BM),&BM);
ClientDC.BitBlt(……)
//使用格式與方法一同
這種方法顯示點陣圖速度較之前一種慢了一點,但其靈活性較大,可以任意變換點陣圖檔案,而無需重新編譯源程式, 也減小了可執行檔案的大小。
實現方法
下面介紹各種圖形顯示技巧的具體實現原理及方法。以下所有程式演算法的實現均可放在視類(CView,也可視自己的需要放在其他類)中處理,且有必要進行如下的相關操作:
增加如下類成員變數:
BITMAP m_Bm;
//儲存點陣圖的寬、高度等資料
HBITMAP *m_hBitmap;
//儲存點陣圖資料控制程式碼
CDC m_MemDC; //記憶體裝置情境物件
在類建構函式中加入如下程式碼:
m_MemDC.CreateCompatibleDC(NULL); //產生記憶體裝置情境物件
m_hBitmap=(HBITMAP *)::LoadImage(
//從檔案中裝入點陣圖資料
AfxGetInstanceHandle(),
“demo1.bmp”,
IMAGE_BITMAP,
0,0,
LR_LOADFROMFILE );
m_MemDC.SelectObject(m_hBitmap); //將點陣圖選入記憶體裝置情境物件
::GetObject(m_hBitmap,sizeof(m_Bm),&m_Bm);
1. 水平交錯效果
原理:將記憶體裝置情境物件(如MemDC)中的點陣圖資料拆分成奇、偶掃描線兩部分,其中奇數條掃描線由上往下移動,偶數條掃描線則由下往上移動,且兩者同時進行。螢幕上的效果為分別由上下兩端出現的較淡柵欄圖形,逐漸相互靠近,直至整個點陣圖完全清楚。垂直交錯效果的實現原理與之類似。
程式演算法:
int i,j;
for ( i=0; i<=m_Bm.bmHeight; i+=2 )
{j = i;
while ( j>0 )
{ClientDC.StretchBlt(
//奇數,由上至下
0,j-1,
//目標裝置邏輯橫、縱座標
m_Bm.bmWidth,1,
//顯示點陣圖的畫素寬、高度
&m_MemDC,
//源點陣圖裝置情境物件
0,m_Bm.bmHeight-(i-j-1),
//源點陣圖的起始橫、縱座標
m_Bm.bmWidth,1,
//源點陣圖的畫素寬、高度
SRCCOPY);
ClientDC.StretchBlt(
//偶數,由下至上
0,m_Bm.bmHeight-j,
//目標裝置邏輯橫、縱座標
m_Bm.bmWidth,1,
//顯示點陣圖的畫素寬、高度
&m_MemDC,
//源點陣圖裝置情境物件
0,i-j,
//源點陣圖的起始橫、縱座標
m_Bm.bmWidth,1,
//源點陣圖的畫素寬、高度
SRCCOPY);
j-=2; }
// while ( j>0 )
Sleep(10);
}
//for ( i=0; i<=m_Bm.bmHeight; i+ =2 )
2. 雨滴效果
原理:將記憶體裝置情境物件(如MemDC)中點陣圖資料的最後一條掃描線,順序地從目標裝置(如ClientDC)中待顯示點陣圖的第一條掃描線所在位置移動至最後一條處,並保留此條掃描線在螢幕上移動時留下的軌跡。接著再把MemDC中點陣圖資料的倒數第二條掃描線,順序地從目標裝置(如ClientDC)中待顯示點陣圖的第一條掃描線所在位置移動至倒數第二條處。其餘的掃描線依此類推。
程式演算法:
int i,j;
for ( i=0; i<=m_Bm.bmHeight; i++ )
{for ( j=0; j<=m_Bm.bmHeight-i; j++ )
ClientDC.StretchBlt(
0,j,
//目標裝置邏輯橫、縱座標
m_Bm.bmWidth,1,
//顯示點陣圖的畫素寬、高度
&m_MemDC,
//源點陣圖裝置情境物件
0,m_Bm.bmHeight-i,
//源點陣圖的起始橫、縱座標
m_Bm.bmWidth,1,
//源點陣圖的畫素寬、高度
SRCCOPY);
Sleep(20);
}
//for ( i=0; i<=m_Bm.bmHeight; i++ )
3. 百葉窗效果
原理:將記憶體裝置情境物件(如MemDC)中的點陣圖資料分成若干組,然後分別從第一組到最後一組進行搬移,第一次搬移每組中第一條掃描線到目標裝置(如ClientDC)中待顯示點陣圖的相應位置,第二次搬移每組中第二條掃描線,接著第三條、第四條掃描線。
程式演算法:
int i,stepi,j;
stepi=m_Bm.bmHeight/10;
for ( i=0; i<=stepi; i++ )
{for ( j=0; j<10; j++ )
ClientDC.StretchBlt(
0,j*stepi+i,
//目標裝置邏輯橫、縱座標
m_Bm.bmWidth,1,
//顯示點陣圖的畫素寬、高度
&m_MemDC,
//源點陣圖裝置情境物件
0,j*stepi+i,
//源點陣圖的起始橫、縱座標
m_Bm.bmWidth,1,
//源點陣圖的畫素寬、高度
SRCCOPY);
Sleep(20);
} //for ( i=0; i<=stepi; i++ )
4. 隨機積木效果
原理:將記憶體裝置情境物件(如MemDC)中的點陣圖資料分成縱橫十等份共一百組資料,然後隨機地取出這一百組資料中的某一組顯示到目標裝置(如ClientDC)中待顯示點陣圖的相應位置,如此反覆直到所有一百組資料均顯示完畢為止。
程式演算法:
int i,j,stepx,stepy,dispnum,x,y;
int pxy[10][10];
//使用本陣列記錄已顯示過的資料組
for ( i=0; i<10; i++ )
for ( j=0; j<10; j++ )
pxy[i][j]=0;
stepx=m_Bm.bmWidth/10;
stepy=m_Bm.bmHeight/10;
srand( (unsigned)time( NULL ) );
dispnum=0;
//記錄已顯示過的資料組的個數
while(1)
{ x=rand() % 10;
y=rand() % 10;
if ( pxy[x][y] )
//本組x,y所代表的資料組是否已顯示過?
continue;
pxy[x][y]=1;
//表明本組x,y所代表的資料組已顯示過
ClientDC.StretchBlt(
x*stepx, y*stepy,
//目標裝置邏輯橫、縱座標
stepx,stepy,
//顯示點陣圖的畫素寬、高度
&m_MemDC,
//源點陣圖裝置情境物件
x*stepx, y*stepy,
//源點陣圖的起始橫、縱座標
stepx,stepy,
//源點陣圖的畫素寬、高度
SRCCOPY);
dispnum++;
if ( dispnum >=100 )
break;
Sleep(30);
} // while(1)
結 語
以上程式程式碼均在Visual C++ 6.0中透過,所有片斷均可編寫成獨立的函式,靈活使用。如果對以上幾種顯示效果進行變換,我們還可以實現多種其他特技效果。
來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/10752043/viewspace-991328/,如需轉載,請註明出處,否則將追究法律責任。
相關文章
- 在visual studio裡圖形化顯示陣列陣列
- C++最好的圖形庫是什麼?C++
- Nginx限流特技Nginx
- C/C++中的實參和形參C++
- canvas 圖形圍繞中心旋轉Canvas
- 使用 Visual C++ 的 Office 自動化C++
- visual studio原生支援C++的含義C++
- 精通Visual C++圖象程式設計------讀書筆記8C++程式設計筆記
- 精通Visual C++圖象程式設計---讀書筆記6.2C++程式設計筆記
- 精通Visual C++圖象程式設計---讀書筆記6.1C++程式設計筆記
- 精通Visual C++圖象程式設計---讀書筆記5C++程式設計筆記
- C++圖片格式轉換:BMP轉JPEGC++
- C++中的輾轉相除法C++
- Use any C++ Compiler with Visual StudioC++Compile
- 好用的向量圖形轉換軟體:vector magic for MacMac
- CSS3的過渡,動畫,圖形轉換CSSS3動畫
- Visual C++ MFC 中常用巨集的含義C++
- 圖形學 旋轉與投影矩陣—2矩陣
- 圖形學 旋轉與投影矩陣-3矩陣
- 圖形學 旋轉與投影矩陣—1矩陣
- CTF中的一些圖形密碼密碼
- Qt場景中圖形項的刪除QT
- 利用Visual Studio除錯WSL下的C++工程除錯C++
- 將編譯過的C++庫迅速部署在Visual Studio新專案中編譯C++
- c++中數字和字串的轉換C++字串
- C++ 表示式中的型別轉換C++型別
- VISUAL-STUDIO(2022)-透過Visual Studio Installer新增C++工作負載C++負載
- gevent安裝錯誤解決方案:Microsoft Visual C++ 14.0 is required. Get it with "Microsoft Visual C++ Build Tools"ROSC++UI
- CAD繪圖工具中的正多邊形命令繪圖
- Visual Studio C++ 安裝以及使用教程C++
- Java的圖形列印Java
- 圖形的認識
- C++中string、char *、char[]、const char*的轉換C++
- c++形參實參C++
- 線性代數在前端中的應用(二):實現滑鼠拖拽旋轉元素、Canvas圖形前端Canvas
- 兩款 Linux 桌面中的圖形化操作 PDF 的工具Linux
- bzoj2697: 特技飛行(貪心)
- Zeit – Linux圖形化中定時任務的工具Linux
- 呼叫Visual Studio的cl.exe編譯C/C++程式編譯C++