2008-09-19 17 views

Trả lời

12

Charlie nhấn vào câu trả lời với WM_NCPAINT. Nếu bạn đang sử dụng MFC, mã sẽ trông giống như sau:

// in the message map 
ON_WM_NCPAINT() 

// ... 

void CMainFrame::OnNcPaint() 
{ 
    // still want the menu to be drawn, so trigger default handler first 
    Default(); 

    // get menu bar bounds 
    MENUBARINFO menuInfo = {sizeof(MENUBARINFO)}; 
    if (GetMenuBarInfo(OBJID_MENU, 0, &menuInfo)) 
    { 
     CRect windowBounds; 
     GetWindowRect(&windowBounds); 
     CRect menuBounds(menuInfo.rcBar); 
     menuBounds.OffsetRect(-windowBounds.TopLeft()); 

     // horrible, horrible icon-drawing code. Don't use this. Seriously. 
     CWindowDC dc(this); 
     HICON appIcon = (HICON)::LoadImage(AfxGetResourceHandle(), MAKEINTRESOURCE(IDR_MAINFRAME), IMAGE_ICON, 16, 16, LR_DEFAULTCOLOR); 
     ::DrawIconEx(dc, menuBounds.right-18, menuBounds.top+2, appIcon, 0,0, 0, NULL, DI_NORMAL); 
     ::DestroyIcon(appIcon); 
    } 
} 
3

Để vẽ trong khu vực không phải khách hàng, bạn cần lấy "cửa sổ" DC (thay vì "khách hàng" DC) và vẽ trong "cửa sổ" DC.

3

Nếu bạn chỉ muốn một cái gì đó trong thanh trình đơn, có thể nó dễ dàng hơn/sạch hơn để thêm nó như là một mục menu phù hợp. Bằng cách này, nó cũng sẽ hoạt động với các chủ đề Windows khác nhau, v.v.

4

Bạn nên thử xử lý WM_NCPAINT. Điều này tương tự như một thông điệp WM_PAINT bình thường, nhưng giao dịch với toàn bộ cửa sổ, thay vì chỉ là khu vực khách hàng. Các tài liệu MSDN trên WM_NCPAINT cung cấp mã mẫu sau:

case WM_NCPAINT: 
{ 
HDC hdc; 
hdc = GetDCEx(hwnd, (HRGN)wParam, DCX_WINDOW|DCX_INTERSECTRGN); 
// Paint into this DC 
ReleaseDC(hwnd, hdc); 
} 

Mã này được thiết kế để được sử dụng trong vòng lặp thông điệp của applicaton của bạn, được giáo luật tổ chức sử dụng một 'chuyển đổi' tuyên bố lớn.

Như đã lưu ý trong ví dụ MFC từ Shog, hãy đảm bảo gọi phiên bản mặc định, trong ví dụ này có nghĩa là một cuộc gọi đến DefWindowProc.