www.gusucode.com > 一个左侧带树形菜单的VC++界面设计实例源码程序 > 一个左侧带树形菜单的VC++界面设计实例/IECtrlBar/IECtrlBar/IEBar.cpp
// IEBar.cpp : implementation file /*********************************************************** Written by : FanWenSheng Address : HeFei University of Technology Email : fanwenshengcom@sohu.com Copyright (c) 2002.8.27 ***********************************************************/ #include "stdafx.h" #include "IECtrlBar.h" #include "IEBar.h" #ifdef _DEBUG #define new DEBUG_NEW #undef THIS_FILE static char THIS_FILE[] = __FILE__; #endif ///////////////////////////////////////////////////////////////////////////// // CIEBar dialog #ifndef IE_FRM_WIDTH #define IE_FRM_WIDTH 6 #endif CIEBar::CIEBar(CWnd* pParent /*=NULL*/) : CDialogBar() { m_TitleTxt = _T("浏览器"); m_cyTitle = 22; m_cxIEBar = 200; pTreeCtrl = NULL; m_HideBtnRc.left = m_HideBtnRc.top = m_HideBtnRc.right = m_HideBtnRc.bottom = 0; m_VirClientRc.left = m_VirClientRc.top = m_VirClientRc.right = m_VirClientRc.bottom = 0; m_PrePnt.x = m_PrePnt.y = 0; m_bResize = m_bTrack = m_bRaised = m_bPressed = false; } void CIEBar::DoDataExchange(CDataExchange* pDX) { CDialogBar::DoDataExchange(pDX); //{{AFX_DATA_MAP(CIEBar) // NOTE: the ClassWizard will add DDX and DDV calls here //}}AFX_DATA_MAP } BEGIN_MESSAGE_MAP(CIEBar, CDialogBar) //{{AFX_MSG_MAP(CIEBar) ON_WM_LBUTTONDBLCLK() ON_WM_LBUTTONDOWN() ON_WM_PAINT() ON_WM_MOUSEMOVE() ON_WM_LBUTTONUP() ON_WM_SETCURSOR() //}}AFX_MSG_MAP END_MESSAGE_MAP() ///////////////////////////////////////////////////////////////////////////// // CIEBar message handlers BOOL CIEBar::InitIEBar() { UpdateData(FALSE); SetWindowText("IE Control Bar"); m_Font.CreateFont(-12,0,0,0,400,0,0,0,134,3,2,1,2,"宋体"); SetFont(&m_Font); // create the tree control pTreeCtrl = new CTreeCtrl(); ASSERT(pTreeCtrl); if(!pTreeCtrl->Create(WS_CHILD | WS_VISIBLE, CRect(0,0,0,0), this, 101)) { TRACE0("Failed to create tree control!"); return FALSE; } // create the tool tip if(!m_TipCtrl.Create(this)) return FALSE; return TRUE; } // for tooltips BOOL CIEBar::PreTranslateMessage(MSG* pMsg) { m_TipCtrl.RelayEvent(pMsg); return CWnd::PreTranslateMessage(pMsg); } BOOL CIEBar::OnSetCursor(CWnd* pWnd, UINT nHitTest, UINT message) { ChangeCursor(); return TRUE; // avoid the cross cursor flash } // change cursor void CIEBar::ChangeCursor() { if(!m_VirClientRc.IsRectEmpty()) { CPoint t_CurPnt; ::GetCursorPos(&t_CurPnt); ScreenToClient(&t_CurPnt); CRect t_CursorRc(m_VirClientRc); t_CursorRc.left = m_VirClientRc.right; t_CursorRc.right = t_CursorRc.left + IE_FRM_WIDTH; HCURSOR hCursor = NULL; if(t_CursorRc.PtInRect(t_CurPnt)) hCursor = AfxGetApp()->LoadCursor(IDC_RESIZE); else hCursor = AfxGetApp()->LoadStandardCursor(IDC_ARROW); ::SetCursor(hCursor); } } void CIEBar::OnLButtonDblClk(UINT nFlags, CPoint point) { // don't floating return; } void CIEBar::OnLButtonDown(UINT nFlags, CPoint point) { SetCapture(); // capture mouse if(!m_HideBtnRc.IsRectEmpty()) { m_bTrack = true; // track enable m_bRaised = false; if(m_HideBtnRc.PtInRect(point)) m_bPressed = true; InvalidateRect(&m_HideBtnRc); } // whether track mouse for risize IE bar CRect t_CursorRc(m_VirClientRc); t_CursorRc.left = m_VirClientRc.right; t_CursorRc.right = t_CursorRc.left + IE_FRM_WIDTH; if(t_CursorRc.PtInRect(point)) m_bResize = true; // don't floating return; } void CIEBar::OnLButtonUp(UINT nFlags, CPoint point) { ReleaseCapture(); m_bTrack = m_bRaised = m_bPressed = false; // hide previous drag line if(m_PrePnt != CPoint(0, 0)) { DrawDragLine(m_PrePnt); m_PrePnt = CPoint(0, 0); } // hide itself if(!m_HideBtnRc.IsRectEmpty()) if(m_HideBtnRc.PtInRect(point)) GetDockingFrame()->ShowControlBar(this, FALSE, FALSE); // adjust IE bar size ResizeIEBar(); m_bResize = false; CDialogBar::OnLButtonUp(nFlags, point); } // adjust IE bar size void CIEBar::ResizeIEBar() { if(m_bResize) { CPoint t_CurPnt; ::GetCursorPos(&t_CurPnt); ScreenToClient(&t_CurPnt); m_cxIEBar = t_CurPnt.x; CRect t_ClientRc; GetClientRect(&t_ClientRc); ClientToScreen(&t_ClientRc); t_ClientRc.right = t_ClientRc.left + m_cxIEBar; // resize right of the "t_ClientRc" if(t_ClientRc.Width() < 11) { t_ClientRc.right = t_ClientRc.left + 11; m_cxIEBar = 11; } else { CRect t_FrmRc; GetDockingFrame()->GetClientRect(&t_FrmRc); if(t_ClientRc.Width() > t_FrmRc.Width() / 2) { t_ClientRc.right = t_ClientRc.left + t_FrmRc.Width() / 2; m_cxIEBar = t_FrmRc.Width() / 2; } } GetDockingFrame()->ShowControlBar(this, FALSE, FALSE); MoveWindow(&t_ClientRc); GetDockingFrame()->ShowControlBar(this, TRUE, FALSE); } } void CIEBar::OnMouseMove(UINT nFlags, CPoint point) { CDialogBar::OnMouseMove(nFlags, point); // draw tracking line if(m_bResize) { // hide previous drag line if(m_PrePnt != CPoint(0, 0)) DrawDragLine(m_PrePnt); // draw new drag line CPoint t_ScrPnt(GetFitPnt()); ClientToScreen(&t_ScrPnt); DrawDragLine(t_ScrPnt); // for draw previous drag line m_PrePnt = t_ScrPnt; } // draw hide-button for raised and pressed DrawHideBtnFace(point); } // draw hide-button for raised and pressed void CIEBar::DrawHideBtnFace(CPoint point) { if(!m_HideBtnRc.IsRectEmpty()) { if(m_HideBtnRc.PtInRect(point)) { SetCapture(); if(m_bRaised) // only draw once return; m_bRaised = m_bTrack ? false : true; m_bPressed = m_bTrack ? true : false; } else { if(!m_bTrack) ReleaseCapture(); if(!m_bRaised && !m_bPressed) // only draw once return; m_bRaised = m_bPressed = false; } InvalidateRect(&m_HideBtnRc); } } // get fit point CPoint CIEBar::GetFitPnt() { CRect t_FrmRc; GetDockingFrame()->GetClientRect(&t_FrmRc); POINT t_CurPnt; ::GetCursorPos(&t_CurPnt); ScreenToClient(&t_CurPnt); if(t_CurPnt.x < 0) return CPoint(0, t_CurPnt.y); if(t_CurPnt.x > t_FrmRc.Width() / 2) return CPoint(t_FrmRc.Width() / 2, t_CurPnt.y); return t_CurPnt; } // draw draging line void CIEBar::DrawDragLine(CPoint point) { CRect t_ClientRect; GetClientRect(&t_ClientRect); ClientToScreen(&t_ClientRect); CRect t_FocusRect(point.x, t_ClientRect.top, point.x, t_ClientRect.bottom); t_FocusRect.InflateRect(2, 0, -2, -43); CDC dc; dc.Attach(::GetWindowDC(NULL)); // note: this dc is used in screen coordinates int t_OldMode = dc.SetROP2(R2_NOT); for(int i=0; i<2; i++) // draw drag lines here { t_FocusRect.left += 2; t_FocusRect.right += 2; dc.DrawFocusRect(&t_FocusRect); } dc.SetROP2(t_OldMode); dc.DeleteDC(); } CSize CIEBar::CalcDynamicLayout(int nLength, DWORD dwMode) { // get rectangle for main frame CRect t_FrmRc; GetDockingFrame()->GetClientRect(&t_FrmRc); // resize tree control size if(pTreeCtrl) { if(pTreeCtrl->m_hWnd != NULL) { CRect t_TreeRc(5, 8, m_cxIEBar-2-IE_FRM_WIDTH, t_FrmRc.Height() - 51); t_TreeRc.top += m_cyTitle + 1; pTreeCtrl->MoveWindow(&t_TreeRc); } } // set IE bar size return CSize(m_cxIEBar, t_FrmRc.Height()); } // get tree control CTreeCtrl* CIEBar::GetTreeCtrl() { if(pTreeCtrl) return pTreeCtrl; else return NULL; } void CIEBar::OnPaint() { CPaintDC dc(this); // device context for painting DrawFrm(dc); // draw big frame for IE bar DrawTitleTxt(dc); // draw title text DrawHideBtn(dc); // draw hide button } // draw big frame for IE bar void CIEBar::DrawFrm(CDC& dc) { CRect t_ClientRc; GetClientRect(&t_ClientRc); t_ClientRc.DeflateRect(3, 6, IE_FRM_WIDTH, 49); dc.SelectStockObject(NULL_BRUSH); dc.Draw3dRect(&t_ClientRc, ::GetSysColor(COLOR_GRAYTEXT), ::GetSysColor(COLOR_GRAYTEXT)); dc.SelectStockObject(WHITE_PEN); // draw left single line dc.MoveTo(t_ClientRc.left + 1, t_ClientRc.top + 1); dc.LineTo(t_ClientRc.left + 1, t_ClientRc.bottom - 1); // draw top single line dc.MoveTo(t_ClientRc.left + 1, t_ClientRc.top + 1); dc.LineTo(t_ClientRc.right - 1, t_ClientRc.top + 1); // draw right single line dc.MoveTo(t_ClientRc.right, t_ClientRc.top); dc.LineTo(t_ClientRc.right, t_ClientRc.bottom); // draw bottom single line dc.MoveTo(t_ClientRc.left, t_ClientRc.bottom); dc.LineTo(t_ClientRc.right + 1, t_ClientRc.bottom); // get virtual rectangle m_VirClientRc = t_ClientRc; m_VirClientRc.InflateRect(-1, -1, 0, 0); } // draw title text void CIEBar::DrawTitleTxt(CDC& dc) { CFont* pOldFont = dc.SelectObject(GetFont()); ASSERT(pOldFont); int t_cxTxt = dc.GetTextExtent(m_TitleTxt).cx; CRect t_TxtRc(m_VirClientRc); t_TxtRc.left += 5; t_TxtRc.right = t_TxtRc.left + t_cxTxt; t_TxtRc.bottom = t_TxtRc.top + m_cyTitle; int t_OldMode = dc.SetBkMode(TRANSPARENT); dc.DrawText(m_TitleTxt, &t_TxtRc, DT_CENTER|DT_VCENTER|DT_SINGLELINE); dc.SelectObject(pOldFont); dc.SetBkMode(t_OldMode); // draw bottom single line for similar to 3d rectangle CPen t_BottomPen(PS_SOLID, 1, ::GetSysColor(COLOR_GRAYTEXT)); CPen* pOldPen = dc.SelectObject(&t_BottomPen); dc.MoveTo(m_VirClientRc.left+1, t_TxtRc.bottom); dc.LineTo(m_VirClientRc.right, t_TxtRc.bottom); dc.SelectObject(pOldPen); } // draw hide button void CIEBar::DrawHideBtn(CDC& dc) { CRect t_HideBtnRc(m_VirClientRc); t_HideBtnRc.right -= 5; t_HideBtnRc.left = t_HideBtnRc.right - m_cyTitle; t_HideBtnRc.bottom = t_HideBtnRc.top + m_cyTitle; t_HideBtnRc.DeflateRect(7, 4, -1, 3); // get hide button rectangle area m_HideBtnRc = t_HideBtnRc; // add a tip for hide button if(m_TipCtrl.GetToolCount()) m_TipCtrl.DelTool(this, 1); m_TipCtrl.AddTool(this, "关闭", t_HideBtnRc, 1); // draw 3d face dc.SelectStockObject(NULL_BRUSH); if(m_bRaised) dc.Draw3dRect(&t_HideBtnRc, ::GetSysColor(COLOR_BTNHIGHLIGHT), ::GetSysColor(COLOR_BTNSHADOW)); else if(m_bPressed) dc.Draw3dRect(&t_HideBtnRc, ::GetSysColor(COLOR_BTNSHADOW), ::GetSysColor(COLOR_BTNHIGHLIGHT)); HICON hIcon = AfxGetApp()->LoadIcon(IDI_HIDE_BTN); ASSERT(hIcon); ::DrawIconEx(dc.m_hDC, t_HideBtnRc.left, t_HideBtnRc.top, hIcon, 16, 16, 0, NULL, DI_NORMAL); }