傳統系統說明檔顯示資訊多採靜態方式,介面單調乏味。專案開發過程中,筆者在各大技術網站搜尋後發現一個優秀的字模顯示控制元件類別,經過擴充實現動態顯示功能,完成後的說明資訊能如電影播放般動態呈現,效果極佳。現將製作流程、程式碼與示範效果分享,期望對相關研究者有所助益。文中顯示的文字內容可依專案需求自行修改。
採用全螢幕顯示方式,但傳統 View 全螢幕效果不佳,改採:主框架移動至螢幕解析度大小 → 移除標題列、功能表列、工具列、狀態列 → 貼上背景圖片 → 載入功能顯示元件。簡單做法是在背景圖上動態建立 CStatic 控制元件,但因系統涉及多功能介面,採用無模式對話方塊形式,建立後 MoveWindow 至指定位置。
// 唯一視窗已初始化,顯示與更新
m_pMainWnd->SetMenu(NULL); // 移除功能表
m_pMainWnd->ModifyStyle(WS_THICKFRAME | WS_CAPTION, NULL); // 修改視窗屬性
m_pMainWnd->MoveWindow(CRect(0, 0,
::GetSystemMetrics(SM_CXSCREEN),
::GetSystemMetrics(SM_CYSCREEN)), TRUE); // 移至螢幕解析度大小
m_pMainWnd->ShowWindow(SW_SHOWMAXIMIZED);
m_pMainWnd->UpdateWindow();
修改 PreCreateWindow(CREATESTRUCT& cs) 函式:
int CMainFrame::OnCreate(LPCREATESTRUCT lpCreateStruct)
{
if (CFrameWnd::OnCreate(lpCreateStruct) == -1)
return -1;
FindWindow("Shell_TrayWnd", NULL)->ShowWindow(SW_HIDE); // 隱藏工作列
return 0;
}
攔截 WM_CLOSE 訊息恢復狀態:
void CMainFrame::OnClose()
{
FindWindow("Shell_TrayWnd", NULL)->ShowWindow(SW_SHOW); // 恢復工作列
CFrameWnd::OnClose();
}
對應 View 的 WM_PAINT 訊息繪製背景,對應 WM_ERASEBKGND 處理螢幕清除,回傳 TRUE:
void CAboutDemoView::OnPaint()
{
CPaintDC dc(this);
HBITMAP hbitmap = ::LoadBitmap(::AfxGetInstanceHandle(), MAKEINTRESOURCE(IDB_BACKBMP));
HDC hMenDC = ::CreateCompatibleDC(NULL);
SelectObject(hMenDC, hbitmap);
::StretchBlt(dc.m_hDC, 0, 0, 1024, 768, hMenDC, 0, 0, 1024, 768, SRCCOPY);
::DeleteDC(hMenDC);
::DeleteObject(hbitmap);
}
CShowAboutDlgCStatic 控制元件並調整位置CShowAboutDlg* m_pAboutDlg = new CShowAboutDlg();
m_pAboutDlg->Create(IDD_ABOUT);
m_pAboutDlg->MoveWindow(CRect(18, 18,
::GetSystemMetrics(SM_CXSCREEN)-13,
::GetSystemMetrics(SM_CYSCREEN)-16), TRUE);
CRect rect;
m_pAboutDlg->GetClientRect(&rect);
m_pAboutDlg->m_AboutCtrl.MoveWindow(rect, TRUE); // 圖片控制元件佔滿客戶區
m_pAboutDlg->ShowWindow(SW_SHOW);
加入專案檔案:ZgMemDC、ZgDraw.h/.cpp、TitleShow.h/.cpp、PublicClass.h/.cpp、AutoFont.h/.cpp。在原作者基礎上修改文字顯示相關程式碼,調整字體符合系統顯示需求。
定義顯示 CStatic 類別物件 TitleShow,在初始化中加入顯示內容。
BOOL CShowAboutDlg::PreTranslateMessage(MSG* pMsg)
{
if (pMsg->message == WM_KEYDOWN)
{
switch (pMsg->wParam)
{
case VK_RETURN:
case VK_ESCAPE:
return TRUE; // 攔截不傳遞預設處理
}
}
return CDialog::PreTranslateMessage(pMsg);
}
完成上述步驟後編譯執行專案,即可看到如電影字幕般動態呈現的系統說明資訊。此法將枯燥的靜態文字轉化為生動的視覺體驗,大幅提升使用者介面的專業度與吸引力。
WM_ERASEBKGND 回傳 TRUE 避免閃爍,StretchBlt 適應不同解析度PreTranslateMessage 過濾特定按鍵防止誤觸關閉