本文提供 dx1 範例的完整 main.h、main.cpp 原始碼,詳細展示從裝置列舉、建立 DirectDraw 物件、取得 IDirectDraw2 介面、設定協作等級、列舉顯示模式到設定顯示模式的完整程式碼實作。
class TForm1 : public TForm {
__published:
// 元件宣告:ComboBox1(裝置), ComboBox2(顯示模式),
// Edit1(狀態), CheckBox1-6(協作旗標), Button1-6(步驟按鈕)
private:
LPDIRECTDRAW FAR lpDD;
LPDIRECTDRAW2 FAR lpDD2;
LPGUID FAR lpDevices[10]; // 列舉裝置 GUID
struct { DWORD Width, Height, Depth, Rate; } DisplayMode[100];
public:
__fastcall TForm1(TComponent* Owner);
};
BOOL WINAPI EnumDeviceCallBack(GUID FAR* lpGUID, LPSTR lpDevice,
LPSTR lpDeviceName, LPVOID lpContext) {
static char i = 0;
lpDevices[i] = lpGUID; // 保存 GUID 指標
Form1->ComboBox1->Items->Add(
AnsiString(lpDevice) + "--" + AnsiString(lpDeviceName));
return (i++ < 10) ? DDENUMRET_OK : DDENUMRET_CANCEL;
}
void __fastcall TForm1::Button1Click(TObject *Sender) {
ComboBox1->Clear();
if (FAILED(DirectDrawEnumerate(EnumDeviceCallBack, NULL)))
Edit1->Text = "Enumerate Devices failed!";
else
Edit1->Text = "Enumerate Devices OK!";
ComboBox1->ItemIndex = 0;
Button1->Enabled = false; Button2->Enabled = true;
}
void __fastcall TForm1::Button2Click(TObject *Sender) {
LPGUID FAR lpD = lpDevices[ComboBox1->ItemIndex];
if (FAILED(DirectDrawCreate(lpD, &lpDD, NULL)))
Edit1->Text = "DirectDraw Create failed!";
else {
Edit1->Text = "DirectDraw Create OK!";
ComboBox1->Enabled = false;
Button2->Enabled = false; Button3->Enabled = true;
}
}
void __fastcall TForm1::Button3Click(TObject *Sender) {
if (FAILED(lpDD->QueryInterface(IID_IDirectDraw2,
(LPVOID*)&lpDD2)))
Edit1->Text = "Get IDirectDraw2 Interface Failed!";
else {
Edit1->Text = "Get IDirectDraw2 Interface OK!";
lpDD->Release(); // 釋放舊介面
Button3->Enabled = false; Button4->Enabled = true;
}
}
void __fastcall TForm1::Button4Click(TObject *Sender) {
DWORD dwFlags = 0;
if (CheckBox1->Checked) dwFlags |= DDSCL_ALLOWMODEX;
if (CheckBox2->Checked) dwFlags |= DDSCL_ALLOWREBOOT;
if (CheckBox3->Checked) dwFlags |= DDSCL_EXCLUSIVE;
if (CheckBox4->Checked) dwFlags |= DDSCL_FULLSCREEN;
if (CheckBox5->Checked) dwFlags |= DDSCL_NORMAL;
if (CheckBox6->Checked) dwFlags |= DDSCL_NOWINDOWCHANGES;
if (FAILED(lpDD2->SetCooperativeLevel(Handle, dwFlags)))
Edit1->Text = "Set cooperative level Failed!";
else {
Edit1->Text = "Set cooperative level OK!";
GroupBox2->Enabled = false;
Button4->Enabled = false; Button5->Enabled = true;
}
}
預設旗標:DDSCL_EXCLUSIVE | DDSCL_FULLSCREEN | DDSCL_NOWINDOWCHANGES
BOOL WINAPI EnumDisplayModesCallBack(LPDDSURFACEDESC lpDesc,
LPVOID lpContext) {
static int i = 0;
char buff[256];
wsprintf(buff, "%dx%dx%dx%d",
lpDesc->dwWidth, lpDesc->dwHeight,
lpDesc->ddpfPixelFormat.dwRGBBitCount,
lpDesc->dwRefreshRate);
Form1->ComboBox2->Items->Add(buff);
DisplayMode[i].Width = lpDesc->dwWidth;
DisplayMode[i].Height = lpDesc->dwHeight;
DisplayMode[i].Depth = lpDesc->ddpfPixelFormat.dwRGBBitCount;
DisplayMode[i].Rate = lpDesc->dwRefreshRate;
return (i++ < 100) ? DDENUMRET_OK : DDENUMRET_CANCEL;
}
void __fastcall TForm1::Button5Click(TObject *Sender) {
ComboBox2->Clear();
if (FAILED(lpDD2->EnumDisplayModes(DDEDM_STANDARDVGAMODES,
NULL, NULL, (LPDDENUMMODESCALLBACK)EnumDisplayModesCallBack)))
Edit1->Text = "Enumerate Display Modes failed!";
else {
Edit1->Text = "Enumerate Display Modes OK!";
ComboBox2->ItemIndex = 0;
Button5->Enabled = false; Button6->Enabled = true;
}
}
void __fastcall TForm1::Button6Click(TObject *Sender) {
if (ComboBox2->ItemIndex < 0) {
ShowMessage("請先選擇顯示方式"); return;
}
if (FAILED(lpDD2->SetDisplayMode(
DisplayMode[ComboBox2->ItemIndex].Width,
DisplayMode[ComboBox2->ItemIndex].Height,
DisplayMode[ComboBox2->ItemIndex].Depth,
DisplayMode[ComboBox2->ItemIndex].Rate, 0)))
Edit1->Text = "Set DisplayMode failed!";
}
void __fastcall TForm1::FormClose(TObject *Sender, TCloseAction &Action) {
if (lpDD2) lpDD2->Release();
}
lpDevices、DisplayMode 為靜態陣列,實際專案建議動態配置。dwRefreshRate、dwFlags。