本主題列出您在撰寫 Direct3D 應用程式時可能會遇到的常見問題類別,以及如何防止它們。
裝置建立
如果您的應用程式在裝置建立期間失敗,請檢查下列常見錯誤。
- 請務必檢查裝置功能,特別是轉譯深度。
- 檢查錯誤碼。 D3DERR_OUTOFVIDEOMEMORY隨時可能發生。
- 使用偵錯 DirectX 動態連結庫 (DLL) 並檢閱調試程式下的輸出訊息。
使用 Lit 頂點
使用已被光照的頂點的應用程式應該藉由將 D3DRS_LIGHTING 渲染狀態設定為 FALSE來停用 Direct3D 照明引擎。 根據預設,啟用光源時,系統會將不包含一般向量的任何頂點的色彩設定為0(黑色),即使輸入頂點包含非零色彩值也一樣。 由於光照頂點本質上不包含頂點法向量,因此如果啟用光照引擎,任何傳遞至 Direct3D 的色彩資訊在轉譯過程中都會遺失。
顯然,頂點色彩對於任何執行自己光源的應用程式都很重要。 若要防止系統強加預設值,請務必將D3DRS_LIGHTING設定為 FALSE。
如果您的應用程式執行但沒有任何顯示,請檢查下列常見錯誤。
- 請確定您的三角形不會變質。
- 請確定您的三角形不會被剔除。
- 請確保您的轉換具有內部的一致性。
- 請檢查檢視區設定,確定它們允許看到您的三角形。
除錯
對 Direct3D 應用程式進行偵錯可能很困難。 除了檢查所有傳回值之外,請嘗試下列技術,這是 Direct3D 程式設計中特別重要的建議,這相依於非常不同的硬體實作。
- 切換至偵錯 DLL。
- 強制僅限軟體的裝置,即使硬體加速可用也一併關閉。
- 強制表面進入系統記憶體。
- 建立選項以在視窗中執行,讓您可以使用整合式調試程式。
此清單中的第二個和第三個選項可協助您避免 Win16 鎖定,否則會導致調試程式停止回應。
此外,請嘗試將下列項目添加至 Win.ini。
[Direct3D]
debug=3
[DirectDraw]
debug=3
Borland Floating-Point 初始化
來自 Borland 的編譯程式會以與 Direct3D 不相容的方式回報浮點例外狀況。 若要解決此問題,請包含_matherr例外狀況處理程式,如下所示:
// Borland floating point initialization
#include <math.h>
#include <float.h>
void initfp(void)
{
// Disable floating point exceptions
_control87(MCW_EM,MCW_EM);
}
int _matherr(struct _exception *e)
{
e; // Dummy reference to catch the warning
return 1; // Error has been handled
}
參數驗證
基於效能考量,Direct3D 立即模式執行階段的調試版本會比零售版本進行更多參數驗證,而零售版本有時甚至完全不進行驗證。 這可讓應用程式使用較慢的偵錯運行時間元件執行強固的偵錯,再使用更快速的零售版本進行效能微調和最終版本。
雖然數個 Direct3D 實時運算模式方法會對可接受的值施加限制,但這些限制通常只會由 Direct3D 即時模式運行時間的偵錯版本檢查並強制執行。 應用程式必須符合這些限制,或在 Direct3D 零售版上執行時,可能會發生無法預期且不想要的結果。 例如,IDirect3DDevice9::DrawPrimitive 方法接受參數(PrimitiveCount),指出方法將呈現的圖元數目。 方法只能接受介於 0 和 D3DMAXNUMPRIMITIVES 之間的值。 在 Direct3D 的偵錯版本中,如果您傳遞的原始圖元數量超過 D3DMAXNUMPRIMITIVES,該方法將優雅地失敗,並將錯誤訊息列印至錯誤記錄檔中,同時將錯誤值返回至您的應用程式。 相反地,如果您的應用程式在運行時間的零售版本執行時發生相同的錯誤,則行為是未定義的。 基於效能考慮,方法不會驗證參數,因此當參數無效時,會產生無法預測且完全的情況行為。 在某些情況下,呼叫可能會運作,在其他情況下,它可能會導致 Direct3D 中的記憶體錯誤。 如果無效的呼叫會持續搭配特定硬體組態和 DirectX 版本運作,則不保證它會繼續在其他硬體或更新版本的 DirectX 上運作。
如果您的應用程式在使用正式版 Direct3D 執行時檔案時遇到不明原因的故障,請針對除錯版本進行測試,並仔細查看您的應用程式傳遞無效參數的情況。 使用 DirectX 控制面板小程式,視需要切換至偵錯運行時間,並檢查 [D3DError 上的中斷] 選項。 此選項會強制運行時間使用 Windows DebugBreak 方法,以強制應用程式在偵測到應用程式錯誤時停止。
相關主題