00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022 #include "StdAfx.h"
00023 #include "Shareaza.h"
00024 #include "CtrlCoolBar.h"
00025 #include "CoolInterface.h"
00026 #include "Skin.h"
00027
00028 #ifdef _DEBUG
00029 #define new DEBUG_NEW
00030 #undef THIS_FILE
00031 static char THIS_FILE[] = __FILE__;
00032 #endif
00033
00034 IMPLEMENT_DYNAMIC(CCoolBarCtrl, CControlBar)
00035
00036 BEGIN_MESSAGE_MAP(CCoolBarCtrl, CControlBar)
00037
00038 ON_WM_CREATE()
00039 ON_WM_TIMER()
00040 ON_WM_HSCROLL()
00041 ON_WM_CTLCOLOR()
00042 ON_WM_MOUSEMOVE()
00043 ON_WM_LBUTTONDOWN()
00044 ON_WM_LBUTTONUP()
00045 ON_WM_LBUTTONDBLCLK()
00046 ON_WM_RBUTTONDOWN()
00047
00048 END_MESSAGE_MAP()
00049
00050 #define DEFAULT_HEIGHT 30
00051 #define GRIPPER_WIDTH 4
00052 #define SEPARATOR_WIDTH 7
00053 #define MARGIN_WIDTH 5
00054
00055 #define BUTTON_WIDTH 9
00056 #define IMAGE_WIDTH 16
00057 #define IMAGEBUTTON_WIDTH 25
00058 #define TEXT_GAP 4
00059 #define CONTROL_HEIGHT 19
00060
00061
00063
00064
00065 CCoolBarCtrl::CCoolBarCtrl()
00066 {
00067 m_bStretch = FALSE;
00068 m_nHeight = DEFAULT_HEIGHT;
00069 m_bGripper = FALSE;
00070 m_bBold = FALSE;
00071 m_bDragForward = FALSE;
00072 m_pSyncObject = NULL;
00073 m_bBuffered = FALSE;
00074 m_bMenuGray = FALSE;
00075
00076 m_pDown = NULL;
00077 m_pHot = NULL;
00078 m_bTimer = FALSE;
00079 m_crBack = 0;
00080 m_bRecalc = FALSE;
00081 }
00082
00083 CCoolBarCtrl::~CCoolBarCtrl()
00084 {
00085 Clear();
00086 }
00087
00089
00090
00091 BOOL CCoolBarCtrl::Create(CWnd* pParentWnd, DWORD dwStyle, UINT nID)
00092 {
00093 CRect rc;
00094 dwStyle |= WS_CHILD;
00095 return CWnd::Create( NULL, NULL, dwStyle, rc, pParentWnd, nID, NULL );
00096 }
00097
00098 void CCoolBarCtrl::SetSize(int nHeight, BOOL bStretch)
00099 {
00100 m_bStretch = bStretch;
00101 m_nHeight = nHeight < 1 ? DEFAULT_HEIGHT : nHeight;
00102
00103 SetWindowPos( NULL, 0, 0, 0, 0,
00104 SWP_DRAWFRAME|SWP_NOMOVE|SWP_NOSIZE|SWP_NOACTIVATE|SWP_NOZORDER );
00105 }
00106
00107 void CCoolBarCtrl::SetGripper(BOOL bGripper)
00108 {
00109 m_bGripper = bGripper;
00110 }
00111
00112 void CCoolBarCtrl::SetBold(BOOL bBold)
00113 {
00114 m_bBold = bBold;
00115 OnUpdated();
00116 }
00117
00118 void CCoolBarCtrl::SetDragForward(BOOL bForward)
00119 {
00120 m_bDragForward = bForward;
00121 }
00122
00123 void CCoolBarCtrl::SetWatermark(HBITMAP hBitmap, BOOL bDetach)
00124 {
00125 if ( m_bmImage.m_hObject )
00126 {
00127 if ( bDetach )
00128 {
00129 m_bmImage.Detach();
00130 }
00131 else
00132 {
00133 m_bmImage.DeleteObject();
00134 }
00135 }
00136
00137 if ( hBitmap ) m_bmImage.Attach( hBitmap );
00138 }
00139
00140 void CCoolBarCtrl::SetSyncObject(CSyncObject* pSyncObject)
00141 {
00142 m_pSyncObject = pSyncObject;
00143 }
00144
00146
00147
00148 CCoolBarItem* CCoolBarCtrl::Add(UINT nID, LPCTSTR pszText, int nPosition)
00149 {
00150 CCoolBarItem* pItem = new CCoolBarItem( this, nID );
00151
00152 if ( nPosition == -1 )
00153 {
00154 m_pItems.AddTail( pItem );
00155 }
00156 else
00157 {
00158 POSITION pos = m_pItems.FindIndex( nPosition );
00159 if ( pos ) m_pItems.InsertBefore( pos, pItem ); else m_pItems.AddTail( pItem );
00160 }
00161
00162 pItem->m_nImage = CoolInterface.ImageForID( nID );
00163
00164 if ( pszText ) pItem->SetText( pszText );
00165
00166 return pItem;
00167 }
00168
00169 CCoolBarItem* CCoolBarCtrl::Add(UINT nCtrlID, int nWidth, int nHeight)
00170 {
00171 CCoolBarItem* pItem = new CCoolBarItem( this, nCtrlID );
00172 m_pItems.AddTail( pItem );
00173
00174 pItem->m_nCtrlID = nCtrlID;
00175 pItem->m_nWidth = nWidth;
00176 pItem->m_nCtrlHeight = nHeight ? nHeight : CONTROL_HEIGHT;
00177
00178 return pItem;
00179 }
00180
00181 CCoolBarItem* CCoolBarCtrl::GetIndex(int nIndex) const
00182 {
00183 for ( POSITION pos = m_pItems.GetHeadPosition() ; pos ; )
00184 {
00185 CCoolBarItem* pItem = (CCoolBarItem*)m_pItems.GetNext( pos );
00186 if ( ! nIndex-- ) return pItem;
00187 }
00188
00189 return NULL;
00190 }
00191
00192 CCoolBarItem* CCoolBarCtrl::GetID(UINT nID) const
00193 {
00194 for ( POSITION pos = m_pItems.GetHeadPosition() ; pos ; )
00195 {
00196 CCoolBarItem* pItem = (CCoolBarItem*)m_pItems.GetNext( pos );
00197 if ( pItem->m_nID == nID ) return pItem;
00198 }
00199
00200 return NULL;
00201 }
00202
00203 int CCoolBarCtrl::GetIndexForID(UINT nID) const
00204 {
00205 int nIndex = 0;
00206
00207 for ( POSITION pos = m_pItems.GetHeadPosition() ; pos ; nIndex++ )
00208 {
00209 CCoolBarItem* pItem = (CCoolBarItem*)m_pItems.GetNext( pos );
00210 if ( pItem->m_nID == nID ) return nIndex;
00211 }
00212
00213 return -1;
00214 }
00215
00216 int CCoolBarCtrl::GetCount() const
00217 {
00218 return m_pItems.GetCount();
00219 }
00220
00221 BOOL CCoolBarCtrl::LoadToolBar(UINT nIDToolBar)
00222 {
00223 CToolBar pToolBar;
00224
00225 if ( ! pToolBar.Create( this ) || ! pToolBar.LoadToolBar( nIDToolBar ) ) return FALSE;
00226
00227 for ( int i = 0 ; i < pToolBar.GetCount(); i++ )
00228 {
00229 UINT nID, nStyle;
00230 int nImage;
00231
00232 pToolBar.GetButtonInfo( i, nID, nStyle, nImage );
00233
00234 Add( nID );
00235 }
00236
00237 return TRUE;
00238 }
00239
00240 void CCoolBarCtrl::Clear()
00241 {
00242 for ( POSITION pos = m_pItems.GetHeadPosition() ; pos ; )
00243 {
00244 delete (CCoolBarItem*)m_pItems.GetNext( pos );
00245 }
00246
00247 m_pItems.RemoveAll();
00248 }
00249
00250 void CCoolBarCtrl::Copy(CCoolBarCtrl* pOther)
00251 {
00252 Clear();
00253
00254 for ( POSITION pos = pOther->m_pItems.GetHeadPosition() ; pos ; )
00255 {
00256 CCoolBarItem* pItem = (CCoolBarItem*)pOther->m_pItems.GetNext( pos );
00257 m_pItems.AddTail( new CCoolBarItem( this, pItem ) );
00258 }
00259 }
00260
00261 UINT CCoolBarCtrl::ThrowMenu(UINT nID, CMenu* pMenu, CWnd* pParent, BOOL bCommand, BOOL bRight)
00262 {
00263 if ( pMenu == NULL ) return 0;
00264 if ( pParent == NULL ) pParent = AfxGetMainWnd();
00265 if ( pParent == NULL ) pParent = this;
00266
00267 m_pDown = GetID( nID );
00268 if ( m_pDown == NULL ) return 0;
00269
00270 m_bMenuGray = TRUE;
00271 Invalidate();
00272 UpdateWindow();
00273
00274 CRect rcButton;
00275 GetItemRect( m_pDown, &rcButton );
00276 ClientToScreen( &rcButton );
00277 rcButton.DeflateRect( 1, 2 );
00278
00279 TPMPARAMS tpm;
00280 tpm.cbSize = sizeof(tpm);
00281 tpm.rcExclude = rcButton;
00282
00283 DWORD nFlags = TPM_LEFTBUTTON|TPM_VERTICAL;
00284
00285 if ( bCommand ) nFlags |= TPM_RETURNCMD;
00286
00287 #if 1
00288 CoolMenu.RegisterEdge( theApp.m_bRTL ? rcButton.right : rcButton.left,
00289 rcButton.bottom, rcButton.Width() );
00290 bRight = FALSE;
00291 #endif
00292
00293 nFlags |= ( bRight ? TPM_RIGHTALIGN : TPM_LEFTALIGN );
00294
00295 UINT nCmd = TrackPopupMenuEx( pMenu->GetSafeHmenu(), nFlags,
00296 bRight || theApp.m_bRTL ? rcButton.right : rcButton.left, rcButton.bottom,
00297 pParent->GetSafeHwnd(), &tpm );
00298
00299 m_bMenuGray = FALSE;
00300 m_pDown = NULL;
00301 Invalidate();
00302
00303 return nCmd;
00304 }
00305
00306 void CCoolBarCtrl::OnUpdated()
00307 {
00308 if ( ! m_bStretch )
00309 {
00310 CSize czLast = m_czLast;
00311
00312 if ( CalcFixedLayout( FALSE, TRUE ) != czLast && m_hWnd)
00313 {
00314 CMDIFrameWnd* pOwner = (CMDIFrameWnd*)GetOwner();
00315
00316 if ( pOwner && pOwner->IsKindOf( RUNTIME_CLASS(CMDIFrameWnd) ) )
00317 {
00318 if ( pOwner->IsIconic() )
00319 m_bRecalc = TRUE;
00320 else
00321 pOwner->RecalcLayout();
00322 }
00323 }
00324 }
00325
00326 if (m_hWnd) Invalidate();
00327 }
00328
00330
00331
00332 int CCoolBarCtrl::OnCreate(LPCREATESTRUCT lpCreateStruct)
00333 {
00334 if ( CControlBar::OnCreate( lpCreateStruct ) == -1 ) return -1;
00335 m_dwStyle |= CBRS_BORDER_3D;
00336 return 0;
00337 }
00338
00339 CSize CCoolBarCtrl::CalcFixedLayout(BOOL bStretch, BOOL bHorz)
00340 {
00341 if ( m_bStretch || bStretch )
00342 {
00343 CSize size( 32000, m_nHeight );
00344
00345 if ( CWnd* pParent = AfxGetMainWnd() )
00346 {
00347 CRect rc;
00348 pParent->GetWindowRect( &rc );
00349 if ( rc.Width() > 32 ) size.cx = rc.Width() + 2;
00350 }
00351
00352 m_czLast = size;
00353
00354 return size;
00355 }
00356 else
00357 {
00358 CSize size( MARGIN_WIDTH * 2 + 5, m_nHeight );
00359 if ( m_bGripper ) size.cx += GRIPPER_WIDTH;
00360
00361 for ( POSITION pos = m_pItems.GetHeadPosition() ; pos ; )
00362 {
00363 CCoolBarItem* pItem = (CCoolBarItem*)m_pItems.GetNext( pos );
00364 if ( pItem->m_bVisible ) size.cx += pItem->m_nWidth;
00365 }
00366
00367 m_czLast = size;
00368
00369 return size;
00370 }
00371 }
00372
00373 void CCoolBarCtrl::PrepareRect(CRect* pRect) const
00374 {
00375 CRect rcClient;
00376 GetClientRect( &rcClient );
00377 CalcInsideRect( rcClient, FALSE );
00378
00379 rcClient.left -= m_cyTopBorder;
00380 rcClient.top -= m_cxLeftBorder;
00381 rcClient.right += m_cyBottomBorder;
00382 rcClient.bottom += m_cxRightBorder;
00383
00384 pRect->SetRect( rcClient.left + MARGIN_WIDTH, rcClient.top + 1, rcClient.right - MARGIN_WIDTH, rcClient.bottom - 1 );
00385 if ( m_bGripper ) pRect->left += GRIPPER_WIDTH;
00386 }
00387
00388 CCoolBarItem* CCoolBarCtrl::HitTest(const CPoint& point, CRect* pItemRect, BOOL bSeparators) const
00389 {
00390 if ( m_pItems.IsEmpty() ) return NULL;
00391
00392 BOOL bRight = FALSE;
00393 CRect rcClient, rcItem;
00394
00395 PrepareRect( &rcClient );
00396 rcItem.CopyRect( &rcClient );
00397
00398 for ( POSITION pos = m_pItems.GetHeadPosition() ; pos ; )
00399 {
00400 CCoolBarItem* pItem = (CCoolBarItem*)m_pItems.GetNext( pos );
00401 if ( ! pItem->m_bVisible ) continue;
00402
00403 if ( pItem->m_nID == ID_RIGHTALIGN && ! bRight )
00404 {
00405 int nRight = 0;
00406 bRight = TRUE;
00407
00408 for ( POSITION pos2 = pos ; pos2 ; )
00409 {
00410 CCoolBarItem* pRight = (CCoolBarItem*)m_pItems.GetNext( pos2 );
00411 if ( pRight->m_bVisible ) nRight += pRight->m_nWidth;
00412 }
00413
00414 if ( rcClient.right - rcItem.left >= nRight )
00415 {
00416 rcItem.left = rcClient.right - nRight;
00417 }
00418 }
00419 else
00420 {
00421 rcItem.right = rcItem.left + pItem->m_nWidth;
00422
00423 if ( rcItem.PtInRect( point ) )
00424 {
00425 if ( pItemRect ) *pItemRect = rcItem;
00426 return ( pItem->m_nID != ID_SEPARATOR || bSeparators ) ? pItem : NULL;
00427 }
00428
00429 rcItem.OffsetRect( rcItem.Width(), 0 );
00430 }
00431 }
00432
00433 return NULL;
00434 }
00435
00436 BOOL CCoolBarCtrl::GetItemRect(CCoolBarItem* pFind, CRect* pRect) const
00437 {
00438 if ( m_pItems.IsEmpty() ) return FALSE;
00439
00440 BOOL bRight = FALSE;
00441 CRect rcClient, rcItem;
00442
00443 PrepareRect( &rcClient );
00444 rcItem.CopyRect( &rcClient );
00445
00446 for ( POSITION pos = m_pItems.GetHeadPosition() ; pos ; )
00447 {
00448 CCoolBarItem* pItem = (CCoolBarItem*)m_pItems.GetNext( pos );
00449 if ( ! pItem->m_bVisible ) continue;
00450
00451 if ( pItem->m_nID == ID_RIGHTALIGN && ! bRight )
00452 {
00453 int nRight = 0;
00454 bRight = TRUE;
00455
00456 for ( POSITION pos2 = pos ; pos2 ; )
00457 {
00458 CCoolBarItem* pRight = (CCoolBarItem*)m_pItems.GetNext( pos2 );
00459 if ( pRight->m_bVisible ) nRight += pRight->m_nWidth;
00460 }
00461
00462 if ( rcClient.right - rcItem.left >= nRight )
00463 {
00464 rcItem.left = rcClient.right - nRight;
00465 }
00466 }
00467 else
00468 {
00469 rcItem.right = rcItem.left + pItem->m_nWidth;
00470
00471 if ( pItem == pFind )
00472 {
00473 *pRect = rcItem;
00474 return TRUE;
00475 }
00476
00477 rcItem.OffsetRect( rcItem.Width(), 0 );
00478 }
00479 }
00480
00481 return FALSE;
00482 }
00483
00484 int CCoolBarCtrl::OnToolHitTest(CPoint point, TOOLINFO* pTI) const
00485 {
00486 CRect rcItem;
00487 CCoolBarItem* pItem = HitTest( point, &rcItem );
00488
00489 if ( pItem == NULL ) return -1;
00490 if ( ! pTI ) return 1;
00491
00492 pTI->uFlags = 0;
00493 pTI->hwnd = GetSafeHwnd();
00494 pTI->uId = (UINT)pItem->m_nID;
00495 pTI->rect = rcItem;
00496 pTI->lpszText = LPSTR_TEXTCALLBACK;
00497
00498 if ( pItem->m_sTip.GetLength() )
00499 {
00500 pTI->lpszText = _tcsdup( pItem->m_sTip );
00501 }
00502 else
00503 {
00504 CString strTip;
00505
00506 if ( LoadString( strTip, pTI->uId ) )
00507 {
00508 if ( LPCTSTR pszBreak = _tcschr( strTip, '\n' ) )
00509 {
00510 pTI->lpszText = _tcsdup( pszBreak + 1 );
00511 }
00512 else
00513 {
00514 BOOL bRTL = FALSE;
00515 if ( theApp.m_bRTL )
00516 {
00517 Skin.GetTextFlowChange( strTip, &bRTL );
00518 if ( bRTL ) strTip.MakeReverse();
00519 }
00520 strTip = strTip.SpanExcluding( _T(".\x2026") );
00521 if ( bRTL ) strTip.MakeReverse();
00522 pTI->lpszText = _tcsdup( strTip );
00523 }
00524 }
00525 }
00526
00527 return pTI->uId;
00528 }
00529
00530 void CCoolBarCtrl::DoPaint(CDC* pDC)
00531 {
00532 ASSERT_VALID( this );
00533 ASSERT_VALID( pDC );
00534
00535 CRect rc;
00536 GetClientRect( &rc );
00537
00538 if ( m_bBuffered || m_bmImage.m_hObject != NULL )
00539 {
00540 CDC* pBuffer = CoolInterface.GetBuffer( *pDC, rc.Size() );
00541
00542 if ( CoolInterface.DrawWatermark( pBuffer, &rc, &m_bmImage ) )
00543 {
00544 CalcInsideRect( rc, FALSE );
00545 rc.left -= m_cyTopBorder;
00546 rc.top -= m_cxLeftBorder;
00547 rc.right += m_cyBottomBorder;
00548 rc.bottom += m_cxRightBorder;
00549 }
00550 else
00551 {
00552 DrawBorders( pBuffer, rc );
00553 }
00554
00555 DoPaint( pBuffer, rc, TRUE );
00556
00557 GetClientRect( &rc );
00558 pDC->BitBlt( 0, 0, rc.Width(), rc.Height(), pBuffer, 0, 0, SRCCOPY );
00559 pBuffer->SelectClipRgn( NULL );
00560 }
00561 else
00562 {
00563 DrawBorders( pDC, rc );
00564 DoPaint( pDC, rc, FALSE );
00565 pDC->FillSolidRect( &rc, CoolInterface.m_crMidtone );
00566 }
00567 }
00568
00569 void CCoolBarCtrl::DoPaint(CDC* pDC, CRect& rcClient, BOOL bTransparent)
00570 {
00571 CRect rcItem( rcClient.left + MARGIN_WIDTH, rcClient.top + 1, rcClient.right - MARGIN_WIDTH, rcClient.bottom - 1 );
00572 CRect rcCopy;
00573
00574 if ( m_bGripper )
00575 {
00576 if ( bTransparent )
00577 {
00578 for ( int nY = rcClient.top + 4 ; nY < rcClient.bottom - 4 ; nY += 2 )
00579 {
00580 pDC->Draw3dRect( rcClient.left + 3, nY, GRIPPER_WIDTH, 1,
00581 CoolInterface.m_crDisabled, CoolInterface.m_crDisabled );
00582 }
00583 }
00584 else
00585 {
00586 for ( int nY = rcClient.top + 4 ; nY < rcClient.bottom - 4 ; nY += 2 )
00587 {
00588 pDC->Draw3dRect( rcClient.left + 3, nY, GRIPPER_WIDTH, 2,
00589 CoolInterface.m_crDisabled, CoolInterface.m_crMidtone );
00590 }
00591
00592 pDC->ExcludeClipRect( rcClient.left + 3, rcClient.top + 4, rcClient.left + GRIPPER_WIDTH + 2, rcClient.bottom - 4 );
00593 }
00594
00595 rcItem.left += GRIPPER_WIDTH;
00596 }
00597
00598 if ( m_pItems.GetCount() == 0 ) return;
00599
00600 CFont* pOldFont = (CFont*)pDC->SelectObject( m_bBold ? &CoolInterface.m_fntBold : &CoolInterface.m_fntNormal );
00601 BOOL bRight = FALSE;
00602
00603 for ( POSITION pos = m_pItems.GetHeadPosition() ; pos ; )
00604 {
00605 CCoolBarItem* pItem = (CCoolBarItem*)m_pItems.GetNext( pos );
00606
00607 if ( pItem->m_nID == ID_RIGHTALIGN && ! bRight )
00608 {
00609 int nRight = 0;
00610 bRight = TRUE;
00611
00612 for ( POSITION pos2 = pos ; pos2 ; )
00613 {
00614 CCoolBarItem* pRight = (CCoolBarItem*)m_pItems.GetNext( pos2 );
00615 if ( pRight->m_bVisible ) nRight += pRight->m_nWidth;
00616 }
00617
00618 if ( rcClient.right - rcItem.left >= nRight + MARGIN_WIDTH )
00619 {
00620 rcItem.left = rcClient.right - nRight - MARGIN_WIDTH;
00621 }
00622 }
00623 else if ( pItem->m_bVisible )
00624 {
00625
00626 rcItem.right = rcItem.left + pItem->m_nWidth;
00627 rcCopy.CopyRect( &rcItem );
00628
00629 CWnd* pCtrl = ( pItem->m_nCtrlID ) ? GetDlgItem( pItem->m_nCtrlID ) : NULL;
00630
00631 pItem->Paint( pDC, rcCopy, m_pDown == pItem,
00632 m_pHot == pItem || ( pCtrl && pCtrl == GetFocus() ),
00633 m_bMenuGray, bTransparent );
00634
00635 if ( ! bTransparent ) pDC->ExcludeClipRect( &rcItem );
00636 if ( pCtrl ) SmartMove( pCtrl, &rcCopy );
00637
00638 rcItem.OffsetRect( rcItem.Width(), 0 );
00639 }
00640 else if ( pItem->m_nCtrlID )
00641 {
00642 CWnd* pCtrl = GetDlgItem( pItem->m_nCtrlID );
00643 if ( pCtrl && pCtrl->IsWindowVisible() ) pCtrl->ShowWindow( SW_HIDE );
00644 }
00645 }
00646
00647 pDC->SelectObject( pOldFont );
00648 }
00649
00650 void CCoolBarCtrl::SmartMove(CWnd* pCtrl, CRect* pRect)
00651 {
00652 CRect rc;
00653 pCtrl->GetWindowRect( &rc );
00654 ScreenToClient( &rc );
00655
00656 if ( rc != *pRect )
00657 {
00658 pCtrl->SetWindowPos( NULL, pRect->left, pRect->top, pRect->Width(),
00659 pRect->Height(), SWP_NOZORDER|SWP_SHOWWINDOW );
00660 }
00661 else if ( ! pCtrl->IsWindowVisible() )
00662 {
00663 pCtrl->ShowWindow( SW_SHOW );
00664 }
00665 }
00666
00667 HBRUSH CCoolBarCtrl::OnCtlColor(CDC* pDC, CWnd* pWnd, UINT nCtlColor)
00668 {
00669 HBRUSH hbr = CControlBar::OnCtlColor( pDC, pWnd, nCtlColor );
00670
00671 if ( nCtlColor == CTLCOLOR_STATIC )
00672 {
00673 pDC->SetBkColor( CoolInterface.m_crMidtone );
00674
00675 if ( m_crBack != CoolInterface.m_crMidtone )
00676 {
00677 if ( m_brBack.m_hObject ) m_brBack.DeleteObject();
00678 m_brBack.CreateSolidBrush( m_crBack = CoolInterface.m_crMidtone );
00679 }
00680
00681 hbr = m_brBack;
00682 }
00683
00684 return hbr;
00685 }
00686
00687 void CCoolBarCtrl::OnUpdateCmdUI(CFrameWnd* pTarget, BOOL bDisableIfNoHndler)
00688 {
00689 UINT nIndex = 0;
00690 BOOL bDirty = FALSE;
00691 BOOL bLocked = FALSE;
00692
00693 if ( m_pSyncObject != NULL )
00694 {
00695 bLocked = m_pSyncObject->Lock( 200 );
00696 }
00697
00698 for ( POSITION pos = m_pItems.GetHeadPosition() ; pos ; )
00699 {
00700 CCoolBarItem* pItem = (CCoolBarItem*)m_pItems.GetNext( pos );
00701
00702 if ( pItem->m_nID == ID_SEPARATOR ) continue;
00703 if ( pItem->m_nCtrlID ) continue;
00704
00705 pItem->m_pOther = this;
00706 pItem->m_nIndex = nIndex++;
00707 pItem->m_nIndexMax = m_pItems.GetCount();
00708 pItem->m_bDirty = FALSE;
00709 BOOL bEnabled = pItem->m_bEnabled;
00710
00711 if ( ! CWnd::OnCmdMsg( pItem->m_nID, CN_UPDATE_COMMAND_UI, pItem, NULL ) )
00712 {
00713 pItem->DoUpdate( pTarget, bDisableIfNoHndler );
00714 }
00715
00716 pItem->m_bDirty |= ( pItem->m_bEnabled != bEnabled );
00717 bDirty |= pItem->m_bDirty;
00718 }
00719
00720 if ( bLocked ) m_pSyncObject->Unlock();
00721
00722 if ( bDirty ) OnUpdated();
00723 }
00724
00725 void CCoolBarCtrl::OnMouseMove(UINT nFlags, CPoint point)
00726 {
00727 CCoolBarItem* pItem = HitTest( point );
00728
00729 if ( m_pDown && m_pDown != pItem ) pItem = NULL;
00730
00731 if ( pItem != m_pHot )
00732 {
00733 m_pHot = pItem;
00734 Invalidate();
00735 }
00736
00737 if ( ! m_bTimer )
00738 {
00739 SetTimer( 1, 100, NULL );
00740 m_bTimer = TRUE;
00741 }
00742
00743 CControlBar::OnMouseMove( nFlags, point );
00744 }
00745
00746 void CCoolBarCtrl::OnTimer(UINT nIDEvent)
00747 {
00748 if ( m_bRecalc )
00749 {
00750 CMDIFrameWnd* pOwner = (CMDIFrameWnd*)GetOwner();
00751
00752 if ( pOwner != NULL && pOwner->IsKindOf( RUNTIME_CLASS(CMDIFrameWnd) ) )
00753 {
00754 if ( ! pOwner->IsIconic() )
00755 {
00756 pOwner->RecalcLayout();
00757 m_bRecalc = FALSE;
00758 }
00759 }
00760 }
00761
00762 if ( nIDEvent == 1 && ( ! m_bMenuGray || m_pDown == NULL ) )
00763 {
00764 CRect rcWindow;
00765 CPoint point;
00766
00767 GetCursorPos( &point );
00768 ScreenToClient( &point );
00769 GetClientRect( &rcWindow );
00770
00771 if ( rcWindow.PtInRect( point ) && GetTopLevelParent()->IsWindowEnabled() )
00772 {
00773 CCoolBarItem* pItem = HitTest( point );
00774
00775 if ( m_pDown && m_pDown != pItem ) pItem = NULL;
00776
00777 if ( pItem != m_pHot )
00778 {
00779 m_pHot = pItem;
00780 Invalidate();
00781 }
00782 }
00783 else
00784 {
00785 KillTimer( nIDEvent );
00786 m_bTimer = FALSE;
00787
00788 if ( m_pHot )
00789 {
00790 m_pHot = NULL;
00791 Invalidate();
00792 }
00793 }
00794 }
00795
00796 CControlBar::OnTimer( nIDEvent );
00797 }
00798
00799 void CCoolBarCtrl::OnLButtonDown(UINT nFlags, CPoint point)
00800 {
00801 CWnd* pFocus = GetFocus();
00802
00803 if ( pFocus && pFocus->GetParent() == this ) SetFocus();
00804
00805 CCoolBarItem* pItem = HitTest( point );
00806
00807 if ( pItem && pItem->m_bEnabled )
00808 {
00809 m_pDown = m_pHot = pItem;
00810 SetCapture();
00811 Invalidate();
00812 return;
00813 }
00814
00815 if ( m_bDragForward )
00816 GetParent()->SendMessage( WM_LBUTTONDOWN, nFlags, MAKELONG( point.x, point.y ) );
00817 else
00818 CControlBar::OnLButtonDown( nFlags, point );
00819 }
00820
00821 void CCoolBarCtrl::OnLButtonUp(UINT nFlags, CPoint point)
00822 {
00823 CCoolBarItem* pItem = HitTest( point );
00824
00825 if ( m_pDown != NULL )
00826 {
00827 BOOL bOn = ( m_pDown == pItem );
00828
00829 m_pDown = NULL;
00830 m_pHot = pItem;
00831
00832 ReleaseCapture();
00833 Invalidate();
00834
00835 if ( bOn ) GetOwner()->PostMessage( WM_COMMAND, pItem->m_nID );
00836
00837 return;
00838 }
00839
00840 if ( m_bDragForward )
00841 GetParent()->SendMessage( WM_LBUTTONUP, nFlags, MAKELONG( point.x, point.y ) );
00842 else
00843 CControlBar::OnRButtonUp( nFlags, point );
00844 }
00845
00846 void CCoolBarCtrl::OnLButtonDblClk(UINT nFlags, CPoint point)
00847 {
00848 CCoolBarCtrl::OnLButtonDown( nFlags, point );
00849 }
00850
00851 void CCoolBarCtrl::OnRButtonDown(UINT nFlags, CPoint point)
00852 {
00853 if ( m_pDown != NULL || m_pHot != NULL )
00854 {
00855 m_pDown = m_pHot = NULL;
00856
00857 ReleaseCapture();
00858 Invalidate();
00859 }
00860
00861 CControlBar::OnRButtonDown( nFlags, point );
00862 }
00863
00865
00866
00867 BOOL CCoolBarCtrl::OnCommand(WPARAM wParam, LPARAM lParam)
00868 {
00869 if ( HIWORD( wParam ) == EN_SETFOCUS ||
00870 HIWORD( wParam ) == EN_KILLFOCUS ) Invalidate();
00871
00872 GetParent()->SendMessage( WM_COMMAND, wParam, lParam );
00873
00874 return CControlBar::OnCommand( wParam, lParam );
00875 }
00876
00877 BOOL CCoolBarCtrl::PreTranslateMessage(MSG* pMsg)
00878 {
00879 if ( pMsg->message == WM_KEYDOWN )
00880 {
00881 if ( pMsg->wParam == VK_RETURN )
00882 {
00883 GetOwner()->PostMessage( WM_COMMAND, MAKELONG( GetDlgCtrlID(), BN_CLICKED ), (LPARAM)GetSafeHwnd() );
00884 }
00885 else if ( pMsg->wParam == VK_ESCAPE )
00886 {
00887 GetOwner()->PostMessage( WM_COMMAND, MAKELONG( GetDlgCtrlID(), BN_DBLCLK ), (LPARAM)GetSafeHwnd() );
00888 }
00889 }
00890
00891 return CControlBar::PreTranslateMessage( pMsg );
00892 }
00893
00894 void CCoolBarCtrl::OnHScroll(UINT nSBCode, UINT nPos, CScrollBar* pScrollBar)
00895 {
00896 GetParent()->SendMessage( WM_HSCROLL, MAKELONG( nSBCode, nPos ), (LPARAM)pScrollBar->GetSafeHwnd() );
00897 }
00898
00899
00901
00902
00903 CCoolBarItem::CCoolBarItem(CCoolBarCtrl* pBar, UINT nID, int nImage)
00904 {
00905 m_pBar = pBar;
00906 m_nID = nID;
00907 m_nImage = nImage;
00908 m_bVisible = TRUE;
00909 m_bEnabled = TRUE;
00910 m_bChecked = FALSE;
00911 m_crText = 0xFFFFFFFF;
00912
00913 switch ( nID )
00914 {
00915 case ID_SEPARATOR:
00916 m_nWidth = SEPARATOR_WIDTH;
00917 break;
00918 case ID_RIGHTALIGN:
00919 m_nWidth = 0;
00920 break;
00921 default:
00922 m_nWidth = IMAGEBUTTON_WIDTH;
00923 break;
00924 }
00925
00926 m_nCtrlID = 0;
00927 m_nCtrlHeight = CONTROL_HEIGHT;
00928 }
00929
00930 CCoolBarItem::CCoolBarItem(CCoolBarCtrl* pBar, CCoolBarItem* pCopy)
00931 {
00932 m_pBar = pBar;
00933 m_nID = pCopy->m_nID;
00934 m_nImage = pCopy->m_nImage;
00935 m_sTip = pCopy->m_sTip;
00936 m_bVisible = pCopy->m_bVisible;
00937 m_bEnabled = pCopy->m_bEnabled;
00938 m_bChecked = pCopy->m_bChecked;
00939 m_crText = pCopy->m_crText;
00940 m_nWidth = pCopy->m_nWidth;
00941
00942 m_nCtrlID = pCopy->m_nCtrlID;
00943 m_nCtrlHeight = pCopy->m_nCtrlHeight;
00944
00945 m_nImage = CoolInterface.ImageForID( m_nID );
00946 SetText( pCopy->m_sText );
00947 }
00948
00949 CCoolBarItem::~CCoolBarItem()
00950 {
00951 }
00952
00954
00955
00956 void CCoolBarItem::Show(BOOL bOn)
00957 {
00958 if ( this == NULL ) return;
00959 if ( m_bVisible == bOn ) return;
00960 m_bVisible = bOn;
00961 m_bDirty = TRUE;
00962 }
00963
00964 void CCoolBarItem::Enable(BOOL bOn)
00965 {
00966 if ( this == NULL ) return;
00967 m_bEnableChanged = TRUE;
00968 m_bEnabled = bOn;
00969 }
00970
00971 void CCoolBarItem::SetCheck(int nCheck)
00972 {
00973 if ( this == NULL ) return;
00974 if ( m_bChecked == ( nCheck == 1 ) ) return;
00975 m_bChecked = ( nCheck == 1 );
00976 m_bDirty = TRUE;
00977 }
00978
00979 void CCoolBarItem::SetText(LPCTSTR lpszText)
00980 {
00981 if ( this == NULL ) return;
00982 if ( m_sText == lpszText ) return;
00983
00984 m_sText = lpszText;
00985 m_bDirty = TRUE;
00986
00987 CDC dc;
00988 dc.Attach( ::GetDC( 0 ) );
00989
00990 CFont* pOld = (CFont*)dc.SelectObject( m_pBar->m_bBold ? &CoolInterface.m_fntBold : &CoolInterface.m_fntNormal );
00991 m_nWidth = BUTTON_WIDTH + dc.GetTextExtent( m_sText ).cx;
00992 if ( m_nImage >= 0 ) m_nWidth += IMAGE_WIDTH + TEXT_GAP;
00993 dc.SelectObject( pOld );
00994
00995 ::ReleaseDC( 0, dc.Detach() );
00996 }
00997
00998 void CCoolBarItem::SetTip(LPCTSTR pszTip)
00999 {
01000 if ( this == NULL ) return;
01001 if ( m_sTip == pszTip ) return;
01002 m_sTip = pszTip;
01003 m_bDirty = TRUE;
01004 }
01005
01006 void CCoolBarItem::SetTextColour(COLORREF crText)
01007 {
01008 if ( this == NULL ) return;
01009 if ( m_crText == crText ) return;
01010 m_crText = crText;
01011 m_bDirty = TRUE;
01012 }
01013
01014 void CCoolBarItem::SetImage(UINT nCommandID)
01015 {
01016 if ( this == NULL ) return;
01017 int nImage = CoolInterface.ImageForID( nCommandID );
01018 if ( nImage == m_nImage ) return;
01019 m_nImage = nImage;
01020 m_bDirty = TRUE;
01021 }
01022
01023 CCoolBarItem* CCoolBarItem::FromCmdUI(CCmdUI* pUI)
01024 {
01025 if ( pUI->m_pOther == NULL ) return NULL;
01026 if ( pUI->m_pOther->IsKindOf( RUNTIME_CLASS(CCoolBarCtrl) ) == FALSE ) return NULL;
01027 return (CCoolBarItem*)pUI;
01028 }
01029
01031
01032
01033 void CCoolBarItem::Paint(CDC* pDC, CRect& rc, BOOL bDown, BOOL bHot, BOOL bMenuGray, BOOL bTransparent)
01034 {
01035 COLORREF crBackground;
01036
01037 if ( m_nID == ID_SEPARATOR )
01038 {
01039 if ( ! bTransparent ) pDC->FillSolidRect( rc.left, rc.top, 3, rc.Height(), CoolInterface.m_crMidtone );
01040 pDC->Draw3dRect( rc.left + 3, rc.top, 1, rc.Height(), CoolInterface.m_crDisabled, CoolInterface.m_crDisabled );
01041 if ( ! bTransparent ) pDC->FillSolidRect( rc.left + 4, rc.top, 3, rc.Height(), CoolInterface.m_crMidtone );
01042 return;
01043 }
01044
01045 if ( m_nCtrlID )
01046 {
01047 for ( int nShrink = rc.Height() - m_nCtrlHeight ; nShrink > 0 ; nShrink -= 2 )
01048 {
01049 if ( ! bTransparent ) pDC->Draw3dRect( &rc, CoolInterface.m_crMidtone, CoolInterface.m_crMidtone );
01050 rc.DeflateRect( 0, 1 );
01051 }
01052 rc.DeflateRect( 1, 0 );
01053 }
01054 else
01055 {
01056 if ( ! bTransparent ) pDC->Draw3dRect( &rc, CoolInterface.m_crMidtone, CoolInterface.m_crMidtone );
01057 rc.DeflateRect( 1, 1 );
01058 }
01059
01060
01061 if ( m_bEnabled && ( bHot || bDown || m_bChecked ) )
01062 {
01063 if ( bMenuGray && bDown )
01064 {
01065 pDC->Draw3dRect( &rc, CoolInterface.m_crDisabled, CoolInterface.m_crDisabled );
01066 }
01067 else
01068 {
01069 pDC->Draw3dRect( &rc, CoolInterface.m_crBorder, CoolInterface.m_crBorder );
01070 }
01071
01072 rc.DeflateRect( 1, 1 );
01073
01074 if ( bMenuGray && bDown )
01075 {
01076 crBackground = CoolInterface.m_crBackNormal;
01077 }
01078 else if ( m_bChecked )
01079 {
01080 crBackground = bHot ? CoolInterface.m_crBackCheckSel : CoolInterface.m_crBackCheck;
01081 }
01082 else
01083 {
01084 crBackground = bDown && bHot ? CoolInterface.m_crBackCheckSel : CoolInterface.m_crBackSel;
01085 }
01086 }
01087 else
01088 {
01089 if ( bTransparent )
01090 {
01091 crBackground = CLR_NONE;
01092 }
01093 else
01094 {
01095 crBackground = CoolInterface.m_crMidtone;
01096 pDC->Draw3dRect( &rc, crBackground, crBackground );
01097 }
01098
01099 rc.DeflateRect( 1, 1 );
01100 }
01101
01102 if ( m_nCtrlID )
01103 {
01104 if ( m_nCtrlHeight == CONTROL_HEIGHT )
01105 {
01106 pDC->Draw3dRect( &rc, CoolInterface.m_crWindow, CoolInterface.m_crWindow );
01107 rc.DeflateRect( 1, 1 );
01108 }
01109 return;
01110 }
01111
01112 if ( crBackground == CLR_NONE )
01113 {
01114 pDC->SetBkMode( TRANSPARENT );
01115 }
01116 else
01117 {
01118 pDC->SetBkMode( OPAQUE );
01119 pDC->SetBkColor( crBackground );
01120 }
01121
01122 if ( m_sText.GetLength() )
01123 {
01124 if ( m_crText != 0xFFFFFFFF )
01125 pDC->SetTextColor( m_crText );
01126 else if ( ! m_bEnabled )
01127 pDC->SetTextColor( CoolInterface.m_crDisabled );
01128 else if ( ( bHot || bDown || m_bChecked ) && ( ! bMenuGray || ! bDown ) )
01129 pDC->SetTextColor( CoolInterface.m_crCmdTextSel );
01130 else
01131 pDC->SetTextColor( CoolInterface.m_crCmdText );
01132
01133 rc.left += ( m_nImage >= 0 ) ? 20 : 1;
01134 int nY = ( rc.top + rc.bottom ) / 2 - pDC->GetTextExtent( m_sText ).cy / 2 - 1;
01135
01136 if ( crBackground == CLR_NONE )
01137 pDC->ExtTextOut( rc.left + 2, nY, ETO_CLIPPED, &rc, m_sText, NULL );
01138 else
01139 pDC->ExtTextOut( rc.left + 2, nY, ETO_CLIPPED|ETO_OPAQUE, &rc, m_sText, NULL );
01140
01141 rc.right = rc.left;
01142 rc.left -= ( m_nImage >= 0 ) ? 20 : 1;
01143 }
01144
01145 if ( m_nImage >= 0 )
01146 {
01147 CPoint ptImage( rc.left + 3, ( rc.top + rc.bottom ) / 2 - 8 );
01148
01149 if ( ! m_bEnabled )
01150 {
01151 ImageList_DrawEx( CoolInterface.m_pImages.GetSafeHandle(), m_nImage, pDC->GetSafeHdc(),
01152 ptImage.x, ptImage.y, 0, 0, crBackground, CoolInterface.m_crShadow, ILD_BLEND50 );
01153 pDC->ExcludeClipRect( ptImage.x, ptImage.y, ptImage.x + 16, ptImage.y + 16 );
01154 }
01155 else if ( m_bChecked )
01156 {
01157 ImageList_DrawEx( CoolInterface.m_pImages.GetSafeHandle(), m_nImage, pDC->GetSafeHdc(),
01158 ptImage.x, ptImage.y, 0, 0, crBackground, CLR_NONE, ILD_NORMAL );
01159 pDC->ExcludeClipRect( ptImage.x, ptImage.y, ptImage.x + 16, ptImage.y + 16 );
01160 }
01161 else if ( ( bHot && ! bDown ) || ( bDown && ! bHot ) )
01162 {
01163 ptImage.Offset( 1, 1 );
01164 pDC->SetTextColor( CoolInterface.m_crShadow );
01165 ImageList_DrawEx( CoolInterface.m_pImages.GetSafeHandle(), m_nImage, pDC->GetSafeHdc(),
01166 ptImage.x, ptImage.y, 0, 0, crBackground, CLR_NONE, ILD_MASK );
01167
01168 ptImage.Offset( -2, -2 );
01169
01170 if ( crBackground != CLR_NONE )
01171 {
01172 pDC->FillSolidRect( ptImage.x, ptImage.y, 18, 2, crBackground );
01173 pDC->FillSolidRect( ptImage.x, ptImage.y + 2, 2, 16, crBackground );
01174 }
01175
01176 ImageList_DrawEx( CoolInterface.m_pImages.GetSafeHandle(), m_nImage, pDC->GetSafeHdc(),
01177 ptImage.x, ptImage.y, 0, 0, CLR_NONE, CLR_NONE, ILD_NORMAL );
01178
01179 pDC->ExcludeClipRect( ptImage.x, ptImage.y, ptImage.x + 18, ptImage.y + 18 );
01180 }
01181 else
01182 {
01183 ImageList_DrawEx( CoolInterface.m_pImages.GetSafeHandle(), m_nImage, pDC->GetSafeHdc(),
01184 ptImage.x, ptImage.y, 0, 0, crBackground, CoolInterface.m_crBackNormal,
01185 bDown ? ILD_NORMAL : ILD_BLEND25 );
01186 pDC->ExcludeClipRect( ptImage.x, ptImage.y, ptImage.x + 16, ptImage.y + 16 );
01187 }
01188 }
01189
01190 if ( crBackground != CLR_NONE ) pDC->FillSolidRect( &rc, crBackground );
01191 }