// MyApp.h
class CMyApp : public CWinApp {
public:
virtual BOOL InitInstance();
virtual int ExitInstance();
private:
ULONG_PTR m_gdiplusToken;
};
// MyApp.cpp
#include
#pragma comment(lib, "gdiplus.lib")
BOOL CMyApp::InitInstance() {
// 初始化 GDI+
Gdiplus::GdiplusStartupInput gdiplusStartupInput;
Gdiplus::GdiplusStartup(&m_gdiplusToken, &gdiplusStartupInput, NULL);
// ... 原有初始化代碼 ...
return TRUE;
}
int CMyApp::ExitInstance() {
// 關閉 GDI+
Gdiplus::GdiplusShutdown(m_gdiplusToken);
return CWinApp::ExitInstance();
}
// MyView.h
class CMyView : public CView {
// ...
protected:
Gdiplus::Image* m_pImage; // 指針,便於錯誤處理
afx_msg void OnPaint();
DECLARE_MESSAGE_MAP()
};
// MyView.cpp
void CMyView::OnInitialUpdate() {
CView::OnInitialUpdate();
// 1. 確定圖片絕對路徑 (示例: 程序目錄下 images 文件夾)
TCHAR szPath[MAX_PATH];
GetModuleFileName(NULL, szPath, MAX_PATH);
PathRemoveFileSpec(szPath);
PathAppend(szPath, _T("images\\test.png")); // 需 #include + lib
// 2. 構造 Image 對象 (支持 png/jpg/bmp/gif/tiff)
m_pImage = new Gdiplus::Image(szPath);
// 3. 關鍵:檢查加載狀態
if (m_pImage->GetLastStatus() != Gdiplus::Ok) {
AfxMessageBox(_T("圖片加載失敗: ") + CString(szPath));
delete m_pImage;
m_pImage = nullptr;
}
}
void CMyView::OnPaint() {
CPaintDC dc(this); // 繪圖設備上下文
if (m_pImage) {
// 4. 創建 GDI+ Graphics 綁定 HDC
Gdiplus::Graphics graphics(dc.m_hDC);
// 5. 設置高質量插值模式 (可選)
graphics.SetInterpolationMode(Gdiplus::InterpolationModeHighQualityBicubic);
// 6. 計算繪製矩形 (居中顯示示例)
CRect rect;
GetClientRect(&rect);
int imgW = m_pImage->GetWidth();
int imgH = m_pImage->GetHeight();
int x = (rect.Width() - imgW) / 2;
int y = (rect.Height() - imgH) / 2;
Gdiplus::Rect destRect(x, y, imgW, imgH);
// 7. 繪製
graphics.DrawImage(m_pImage, destRect);
}
// 不要調用 CView::OnPaint() 進行繪圖文檔視圖架構除外
}
void CMyView::OnDestroy() {
if (m_pImage) {
delete m_pImage;
m_pImage = nullptr;
}
CView::OnDestroy();
}
// 在 OnInitDialog 中加載
BOOL CMyDlg::OnInitDialog() {
CDialogEx::OnInitDialog();
// ... 加載 m_pImage 同前 ...
return TRUE;
}
// 在 OnPaint 中繪製
void CMyDlg::OnPaint() {
CPaintDC dc(this);
if (m_pImage) {
Gdiplus::Graphics g(dc.m_hDC);
CRect rc;
GetClientRect(&rc);
g.DrawImage(m_pImage, 0, 0, rc.Width(), rc.Height()); // 拉伸填充
}
// CDialogEx::OnPaint() 會繪製背景/控件,通常最後調用或不調用
CDialogEx::OnPaint();
}
| 現象 | 可能原因 | 解決 |
|---|---|---|
| 空白無圖片 | GDI+ 未啟動 | App::InitInstance 調用 GdiplusStartup |
| 運行時崩潰 | m_pImage 為 nullptr 仍調用 DrawImage | 繪製前判斷 if (m_pImage) |
| 找不到文件 | 相對路徑 "test.png" 發布後失效 | 用 GetModuleFileName 獲取程序目錄拼接絕對路徑 |
| 圖片變形/不全 | 目標矩形尺寸錯誤 | 計算 destRect 根據客戶區與圖片原始尺寸 |
| 內存泄漏 | 未 delete m_pImage / 未 GdiplusShutdown | OnDestroy/ExitInstance 釋放 |
MFC 顯示圖片三步走:**App 初始化 GDI+ → 視圖/對話框 OnInitialUpdate/OnInitDialog 加載 Image 檢查狀態 → OnPaint 中 Graphics::DrawImage 繪製**。嚴格檢查 `GetLastStatus()`、使用絕對路徑、正確釋放資源,即可穩定顯示 PNG/JPG 等格式圖片。