//从CPropertySheet派生一个新类
//具有自绘题头功能
#pragma once // OwnerDraw_PropertySheet.h : header file // ///////////////////////////////////////////////////////////////////////////// // COwnerDraw_PropertySheet class COwnerDraw_PropertySheet : public CPropertySheet { DECLARE_DYNAMIC(COwnerDraw_PropertySheet) // Construction public: COwnerDraw_PropertySheet(); COwnerDraw_PropertySheet(UINT nIDCaption, CWnd* pParentWnd = NULL, UINT iSelectPage = 0); COwnerDraw_PropertySheet(LPCTSTR pszCaption, CWnd* pParentWnd = NULL, UINT iSelectPage = 0); // Attributes public: // Operations public: INT InsertPage(CPropertyPage* pPage, INT nIndex=-1); // Overrides // ClassWizard generated virtual function overrides //{{AFX_VIRTUAL(COwnerDraw_PropertySheet) public: virtual BOOL OnInitDialog(); //}}AFX_VIRTUAL // Implementation public: virtual ~COwnerDraw_PropertySheet(); // Generated message map functions protected: //{{AFX_MSG(COwnerDraw_PropertySheet) afx_msg void OnDrawItem(int nIDCtl, LPDRAWITEMSTRUCT lpDrawItemStruct); afx_msg void OnSize(UINT nType, int cx, int cy); //}}AFX_MSG DECLARE_MESSAGE_MAP() virtual LRESULT WindowProc(UINT message, WPARAM wParam, LPARAM lParam); virtual BOOL OnNotify(WPARAM wParam, LPARAM lParam, LRESULT* pResult); protected: void Comm_Init(); protected: COLORREF m_crSelColour, m_crGrayColour; CFont m_SelFont, m_UnselFont; };
// OwnerDraw_PropertySheet.cpp : implementation file // #include "stdafx.h" #include "OwnerDraw_PropertySheet.h" #ifdef _DEBUG #define new DEBUG_NEW #undef THIS_FILE static char THIS_FILE[] = __FILE__; #endif ///////////////////////////////////////////////////////////////////////////// // COwnerDraw_PropertySheet IMPLEMENT_DYNAMIC(COwnerDraw_PropertySheet, CPropertySheet) COwnerDraw_PropertySheet::COwnerDraw_PropertySheet():CPropertySheet() { Comm_Init(); } COwnerDraw_PropertySheet::COwnerDraw_PropertySheet(UINT nIDCaption, CWnd* pParentWnd, UINT iSelectPage) :CPropertySheet(nIDCaption, pParentWnd, iSelectPage) { Comm_Init(); } COwnerDraw_PropertySheet::COwnerDraw_PropertySheet(LPCTSTR pszCaption, CWnd* pParentWnd, UINT iSelectPage) :CPropertySheet(pszCaption, pParentWnd, iSelectPage) { Comm_Init(); } void COwnerDraw_PropertySheet::Comm_Init() { } COwnerDraw_PropertySheet::~COwnerDraw_PropertySheet() { m_SelFont.DeleteObject(); m_UnselFont.DeleteObject(); } BEGIN_MESSAGE_MAP(COwnerDraw_PropertySheet, CPropertySheet) //{{AFX_MSG_MAP(COwnerDraw_PropertySheet) ON_WM_DRAWITEM() ON_WM_SIZE() //}}AFX_MSG_MAP END_MESSAGE_MAP() ///////////////////////////////////////////////////////////////////////////// // COwnerDraw_PropertySheet message handlers BOOL COwnerDraw_PropertySheet::OnInitDialog() { BOOL bResult = CPropertySheet::OnInitDialog(); // TODO: Add your specialized code here CTabCtrl *pTabCtrl = GetTabControl(); pTabCtrl->ModifyStyle(0, TCS_OWNERDRAWFIXED ); //使之具有自绘功能 m_crSelColour = RGB(0,0,255); //选中字体颜色 m_crGrayColour = RGB(128,128,128); //灰字体颜色 //创建字体 CFont *pFont = pTabCtrl->GetFont(); LOGFONT mLogFont, mSelLogFont; pFont->GetLogFont(&mLogFont); mSelLogFont = mLogFont; mSelLogFont.lfWeight = FW_ULTRABOLD; m_SelFont.DeleteObject(); m_SelFont.CreateFontIndirect(&mSelLogFont); m_UnselFont.DeleteObject(); m_UnselFont.CreateFontIndirect(&mLogFont); return bResult; } void COwnerDraw_PropertySheet::OnDrawItem(int nIDCtl, LPDRAWITEMSTRUCT lpDrawItemStruct) { // TODO: Add your message handler code here and/or call default CPropertySheet::OnDrawItem(nIDCtl, lpDrawItemStruct); if(lpDrawItemStruct->CtlType == ODT_TAB) { CTabCtrl *pTabCtrl = GetTabControl(); CRect rect = lpDrawItemStruct->rcItem; INT nTabIndex = lpDrawItemStruct->itemID; if (nTabIndex < 0) return; TCHAR label[64]; TC_ITEM tci; tci.mask = TCIF_TEXT|TCIF_IMAGE; tci.pszText = label; tci.cchTextMax = 63; pTabCtrl->GetItem(nTabIndex, &tci ); CDC* pDC = CDC::FromHandle(lpDrawItemStruct->hDC); if (!pDC) return; int nSavedDC = pDC->SaveDC(); // For some bizarre reason the rcItem you get extends above the actual drawing area. We have to workaround this "feature". rect.top += ::GetSystemMetrics(SM_CYEDGE); pDC->SetBkMode(TRANSPARENT); //pDC->FillSolidRect(rect, ::GetSysColor(COLOR_BTNFACE)); // Draw image CImageList* pImageList = pTabCtrl->GetImageList(); if (pImageList && tci.iImage >= 0) { rect.left += pDC->GetTextExtent(_T(" ")).cx; // Margin // Get height of image so we IMAGEINFO info; pImageList->GetImageInfo(tci.iImage, &info); CRect ImageRect(info.rcImage); INT nYpos = rect.top; pImageList->Draw(pDC, tci.iImage, CPoint(rect.left, nYpos), ILD_TRANSPARENT); rect.left += ImageRect.Width(); } COLORREF txtColor = GetSysColor(COLOR_WINDOWTEXT); CFont *pSelFont = 0; if (lpDrawItemStruct->itemState & CDIS_SELECTED ) { rect.top -= ::GetSystemMetrics(SM_CYEDGE); txtColor = m_crSelColour; pSelFont = &m_SelFont; } else if(lpDrawItemStruct->itemState & (CDIS_DISABLED | CDIS_GRAYED) ) { txtColor = m_crGrayColour; pSelFont = &m_UnselFont; } else { } pDC->SetTextColor(txtColor); if(pSelFont) pDC->SelectObject(pSelFont); pDC->DrawText(label, rect, DT_SINGLELINE|DT_VCENTER|DT_CENTER); pDC->RestoreDC(nSavedDC); } } void COwnerDraw_PropertySheet::OnSize(UINT nType, int cx, int cy) { CPropertySheet::OnSize(nType, cx, cy); // TODO: Add your message handler code here if(!GetSafeHwnd()) return; CTabCtrl *pCtrl = GetTabControl(); if(pCtrl) { CRect SheetRect; GetClientRect(&SheetRect); CRect PageRect = SheetRect; pCtrl->AdjustRect(0, PageRect); for(INT nPage=0; nPage<GetPageCount(); nPage++) { CPropertyPage *pPage = GetPage(nPage); if(pPage && pPage->GetSafeHwnd()) { pPage->MoveWindow( &PageRect ); //pPage->PostMessage(WM_SIZE); } } } } LRESULT COwnerDraw_PropertySheet::WindowProc(UINT message, WPARAM wParam, LPARAM lParam) { // TODO: 在此添加专用代码和/或调用基类 if(WM_ERASEBKGND == message) return TRUE; if(WM_PAINT == message) { PAINTSTRUCT ps; CDC *pDC = BeginPaint(&ps); EndPaint(&ps); return(0); } return CPropertySheet::WindowProc(message, wParam, lParam); } INT COwnerDraw_PropertySheet::InsertPage(CPropertyPage* pPage, INT nIndex) { ASSERT_VALID(this); ENSURE_VALID(pPage); ASSERT_KINDOF(CPropertyPage, pPage); if(nIndex < 0 || nIndex > GetPageCount())//add to end { nIndex = GetPageCount(); } // add page to internal list m_pages.InsertAt(nIndex, pPage); // add page externally if (m_hWnd != NULL) { // build new prop page HPROPSHEETPAGE hPSP = AfxCreatePropertySheetPage(&pPage->GetPSP()); if (hPSP == NULL) AfxThrowMemoryException(); if (!SendMessage(PSM_INSERTPAGE, nIndex, (LPARAM)hPSP)) { AfxDestroyPropertySheetPage(hPSP); AfxThrowMemoryException(); } ++m_psh.nPages; } return nIndex; } BOOL COwnerDraw_PropertySheet::OnNotify(WPARAM wParam, LPARAM lParam, LRESULT* pResult) { // TODO: 在此添加专用代码和/或调用基类 static NMHDR nmh; nmh = *((LPNMHDR)lParam); nmh.hwndFrom = GetSafeHwnd(); BOOL bRet = CPropertySheet::OnNotify(wParam, lParam, pResult); GetParent()->PostMessage(WM_NOTIFY, GetDlgCtrlID(), (LPARAM)&nmh); return bRet; }