亚洲免费在线-亚洲免费在线播放-亚洲免费在线观看-亚洲免费在线观看视频-亚洲免费在线看-亚洲免费在线视频

游戲編輯器框架教程

系統 1853 0

-------------------------------------------------------
游戲編輯器框架教程
無心柳
-------------------------------------------------------

一、前言:

我一直在尋找DX編程和MFC類庫的結合點,前段時間曾經在第二人生http//webking.com.cn/secondlife上放了一個從《計算機編程技巧與雜志》來的例子。應該說,那個例子非常不錯,唯一的缺點就是它只研究了全屏幕顯示的情況,而對于地圖編輯器人員來說,迫切需要的是既能夠完全使用原有MFC的框架又能夠使用DX的功能的東西,這也是我一直在尋找的,今天(1999/12/4)總算找到了。

促使我找到這個辦法的是為MUD編寫的那個地圖編輯器,雖然功能上沒有什么欠缺,但誠如美工所言,界面太差了,按鈕按下去的時候沒有一個響應動作,而且也不方便使用MFC的全部功能。在完成這個地圖編輯器以后,其他程序員的MFC編輯器也在趕制之中,而他們的圖形顯示部分是一個難題。如果要使用經典編程方法去操作和顯示256色以上的圖片,在程序上是非常麻煩的。能否將 MFC與DDRAW的窗口模式完美地融合 ?在完成地圖編輯器以后,我已經有了這樣的設想,就等著拿到機器上去測試了。結果一試之下,完全可行,而且它是如此地 簡單

二、第一個例子:

在這個例子中,我用VC的AppWizard生成了一個標準的單文檔窗口并保存。然后,在視類CGameEditView的頭文件中加入了四個DX成員,一個DDRAW指針,一個DDRAW4指針,一個前緩沖,一個后緩沖,具體可以看源碼。在頭文件中,另外加入了兩個函數,一個是Msg函數,用于顯示消息框,這是從別人的例子中直接復制過來的;另一個是InitDDrawSurface()函數。然后在CGameEditView.cpp里加入了這兩個函數的函數體。Msg沒什么說的,你直接復制上去用就行了。InitDDrawSurface你也可以直接復制,這個函數里創建了一個DDRAW對象,再利用它獲取了DDRAW4的接口。然后用DDRAW4接口創建一個DDSURFACE4主屏幕緩沖頁,它負責在屏幕上顯示內容。最后創建一個DDSURFACE4的后臺緩沖頁,它負責在主緩沖在屏幕上顯示之前在后臺準備一下畫面。僅此兩個函數而已。

程序中有兩個動作,一個是在預創建窗口時執行InitDDrawSurface()對DDRAW頁面進行初始化,如果不成功程序就退出。另一個動作就是在視類的OnDraw()中將一塊矩形區域從后臺緩沖復制到前緩沖(也就是在屏幕上顯示出來)。由于后臺緩沖沒有放入數據,所以顯示的內容將是隨機的,一般是黑色的。顯示的步驟可以看源碼上的程序注釋,我一般寫得比較細。

為什么不加入什么撞球等的變化動作?這是因為我只想告訴大家一個最簡單的DDRAW窗口頁面如何創建和使用,下面的教程中會慢慢加入如何讀入位圖塊和顯示,時間控制,窗口區域檢測,剪切塊,顏色鍵等內容。當教程結束的時候,用MFC和DDRAW做一個簡單游戲應該沒有問題了。

下載源碼 GameEdit1.zip

三、第二個例子:

1、上個例子中有個明顯的漏洞,在InitDDrawSurface()中創建后臺緩沖的時候,顯式地指定了寬和高。在前緩沖lpMainSurface創建時,沒有指定大小,因為不需要,前緩沖指的就是整個屏幕的范圍,它使用的是顯示內存。而后緩沖是不顯示的內容,它實際是在系統內存中(窗口模式不能在顯示內存中再創建后臺頁面)創建的一個頁面,一般情況下,應該設置得和前緩沖一樣大或者更大。1024*768的顯式指定對一般顯示器可能夠了,但萬一用戶使用更大的分辨率就可能導致錯誤。所以第二個例子中首先修改了InitDDrawSurface()中創建后臺緩沖的部分,用標準WINDOWS函數GetDeivceCaps獲取了當前顯示分辯率的高和寬(當然也可以獲得顏色位數,源碼中有)。然后用獲取的高和寬來創建后臺緩沖,這樣就保證了與分辨率的大小相同。當然這也不是絕對保險,萬一用戶運行中修改了分辨率仍有可能導致錯誤,但一般我們不需要為那種情況負責了,可以不去考慮。

2、這次我們要讀入一個圖片,看起來挺恐怖,你好象需要去研究BITMAP的文件結構。其實不需要那么復雜,對一般的游戲和編輯器來說,根本不用去了解那些細節的問題,在DX的例程中多次用到的兩個文件可以直接搬過來用,它們是ddutil.h和ddutil.cpp,你可以在大部分DX的例程中找到它們,然后復制到你程序的文件夾下,再在工程中加入這兩個文件,試試重編譯。直接重編譯是無法成功的,這是因為MFC程序有點特殊性,要使它能被MFC所用,必須在上面提到的這兩個文件首部都追加一句#include "stdafx.h"。用過這個語句,MFC就認這兩個文件,然后可以正常編譯通過。當然,如果你想在VIEW類中使用里的函數,還要在GameEditView.cpp的頭部加入#include "ddutil.h"。這是常識,說這些好象有點多余,在源碼中這幾個步驟都做了而且有說明。

3、通過第2步,已經可以隨時讀入BMP文件了,具體的讀法是非常簡單的,因為你已經可以使用ddutil.cpp里的函數。如果需要,你也可以去修改這個文件的源碼或者制作修改版。作為例子,我先在GameEditView.h中增加了一個DDSURFACE4的頁面指針:

LPDIRECTDRAWSURFACE4 lpBitMapBuffer;//DirectDraw讀入的位圖頁面保存在這里

再在GameEditView.cpp的預創建窗口PreCreateWindow()函數中將一幅位圖讀入這個位圖頁面。讀入成功后,將這個臨時頁面的內容復制到后臺緩沖。這樣,后臺緩沖就有了內容。再編譯一次程序,會發現原來窗口左上角那個黑塊已經變成這幅圖片(一幅UO中截下來的騎馬圖),代碼如下:

lpBitMapBuffer=DDLoadBitmap(lpDD4,"test.bmp",200,200);
if(NULL==lpBitMapBuffer)//如果沒有讀入成功,退出程序
{
Msg("無法裝入位圖,演示無法進行");
exit(-2);
}
//讀入成功就復制到后臺緩沖去
lpBackBuffer->BltFast(0,0,lpBitMapBuffer,&(CRect(0,0,200,200)),FALSE);

你可以看到代碼中指定的位圖文件名是test.bmp,所以你也需要一個這樣文件名的位圖文件,在下面的源碼包里附有一個,如果你想換一個文件也可以,不過這個文件以后將用于演示動畫的例子。

第二個例子完,需要的話請下載源碼 GameEdit2.zip

三、與GDI結合:

上面的兩個例子的源碼中沒有包含資源文件,所以在使用的時候請先按照上面提到的方法建立自己的簡單MFC單文檔程序,再將源碼文件替換你自己的文件再編譯。

在第二個例子中,讀入了一幅位圖并顯示在窗口的左上角。這在程序運行中沒有任何問題,而且速度還相當快。但如果你同時運行了其他程序,或者將窗口移動到屏幕的邊緣位置,會出現一些不正常現象。如果將窗口移動到屏幕邊緣,在從后臺到前臺進行傳送的時候,會發生非常矩形錯誤,意思是指你試圖將頁面傳送到屏幕區域外,也就是前緩沖以外(前面說過,前緩沖與屏幕大小是一樣的)。其結果并不會使你的程序當機,只是這次傳送不會進行。另外,當你用其他程序的窗口蓋住本程序窗口并移動上面的窗口的時候,本窗口的刷新可能導致將位圖蓋在其他窗口區域內。這是個嚴重的問題,在編寫全屏幕程序的時候不會發生這種情況,因為屏幕被你的程序獨占了,而在編寫窗口程序的時候,你的程序就會顯示非常差勁。

要解決上面的問題,一個辦法是當程序失去焦點的時候,你就禁止將位圖從后緩沖傳送到前緩沖,當重新獲得焦點的時候,再恢復位圖傳送。但有時候這樣不理想,比如你在進行程序或者游戲的時候,同時發ICQ的信息,雖然ICQ占的屏幕面積不大,還是會導致你的程序停止更新畫面,而如果你在游戲中此時正在緊張而且隨時需要你干預的話,程序看起來就非常不友好。

另一個辦法是與GDI結合,與GID結合會導致在圖像速度上有微小的下降,但會使你的程序看來非常自然。其實方法也非常簡單,就是獲取后臺緩沖的HDC,然后用HDC的BitBlt方法將后臺緩沖復制給窗口CDC,可以將OnDraw中的BltFast的方法修改為:

HDC hdc;

lpBackBuffer->GetDC(&hdc); //獲得后臺緩沖的HDC

::BitBlt(pDC->m_hDC,0,0,100,100,hdc,0,0,SRCCOPY); //將后臺緩沖的圖片傳送到窗口DC

lpBackBuffer->ReleaseDC(hdc); //不要忘了用完后釋放HDC,否則會出錯

為了與HDC匹配,所以使用pDC的成員m_hDC。BitBlt的具體用法可以看一下幫助文件。使用這個辦法以后,無論你將窗口移動到什么位置,以及無論你用什么窗口蓋住程序的窗口,都不會有任何不正常的現象發生。它唯一的缺點就是比BltFast慢一點點。因為DC的處理方法是分幾次進行,第一次復制到一個DC自己的后臺緩沖,然后根據窗口的合法區域分一次或多次復制到屏幕。所以這個方法適用于制作編輯器以及對速度不是極度敏感的游戲。如果要達到最高速度,當然是非全屏幕模式莫屬。

?



Trackback: http://tb.blog.csdn.net/TrackBack.aspx?PostId=3405


游戲編輯器框架教程


更多文章、技術交流、商務合作、聯系博主

微信掃碼或搜索:z360901061

微信掃一掃加我為好友

QQ號聯系: 360901061

您的支持是博主寫作最大的動力,如果您喜歡我的文章,感覺我的文章對您有幫助,請用微信掃描下面二維碼支持博主2元、5元、10元、20元等您想捐的金額吧,狠狠點擊下面給點支持吧,站長非常感激您!手機微信長按不能支付解決辦法:請將微信支付二維碼保存到相冊,切換到微信,然后點擊微信右上角掃一掃功能,選擇支付二維碼完成支付。

【本文對您有幫助就好】

您的支持是博主寫作最大的動力,如果您喜歡我的文章,感覺我的文章對您有幫助,請用微信掃描上面二維碼支持博主2元、5元、10元、自定義金額等您想捐的金額吧,站長會非常 感謝您的哦!!!

發表我的評論
最新評論 總共0條評論
主站蜘蛛池模板: 日本免费在线视频 | 免费欧美一级 | 久久久综合香蕉尹人综合网 | bbw下身丰满18ⅹxxⅹ | 成人久久伊人精品伊人 | 91粉色视频在线观看 | 久久久精品日本一区二区三区 | 国产伦一区二区三区免费 | 亚洲另类伦春色综合妖色成人网 | 日日天日日夜日日摸 | 日本成人毛片 | 精品国产精品国产 | 亚洲图片综合网 | 在线观看日本一区 | 成人免费观看网欧美片 | 国产在线麻豆一区二区 | 久久国产精品999 | 日本道在线视频 | 四虎亚洲 | 九九久久九九 | 高清黄色直接看 | 成人深夜视频在线观看 | 欧美亚洲综合另类型色妞 | 97精品视频 | 午夜视频在线观看国产www | 欧美视频在线观看一区二区 | 久久精品午夜视频 | 久久精品免费大片国产大片 | 99国产精品免费观看视频 | 四虎影视成人永久在线播放 | 7777成年大片免费播放器 | 国产精品免费久久 | 四虎影院免费视频 | 99热久久这里只精品国产ww | 国产精品国产福利国产秒拍 | 热99re国产久热在线 | 国产精品久久久久久久免费大片 | 中文字幕人成不卡一区 | 一级特黄高清完整大片 | 日操夜操天天操 | 亚洲一级黄色大片 |