GME  13
GMEConstraintTreeCtrl.cpp
Go to the documentation of this file.
00001 //###############################################################################################################################################
00002 //
00003 //      Object Constraint Language Generic Manager
00004 //      GMEConstraintTreeCtrl.cpp
00005 //
00006 //###############################################################################################################################################
00007 
00008 #include "StdAfx.h"
00009 #include "GMEConstraintTreeCtrl.h"
00010 
00011 #ifdef _DEBUG
00012 #define new DEBUG_NEW
00013 #undef THIS_FILE
00014 static char THIS_FILE[] = __FILE__;
00015 #endif
00016 
00017 int static CALLBACK SpecialCompare( LPARAM lParam1, LPARAM lParam2, LPARAM lParamSort )
00018 {
00019         CConstraintTreeCtrl* pTree = (CConstraintTreeCtrl*) lParamSort;
00020         int iImNum1, iImNum2;
00021         pTree->GetItemImage( ( HTREEITEM ) lParam1, iImNum1, iImNum1 );
00022         pTree->GetItemImage( ( HTREEITEM ) lParam2, iImNum2, iImNum2 );
00023 
00024         CString strCaption1 = pTree->GetItemText( ( HTREEITEM ) lParam1 );
00025         CString strCaption2 = pTree->GetItemText( ( HTREEITEM ) lParam2 );
00026 
00027         if ( iImNum1 < iImNum2 )
00028                 return -1;
00029         if ( iImNum1 > iImNum2 )
00030                 return 1;
00031         return _tcscmp( strCaption1, strCaption2 );
00032 }
00033 
00034 //##############################################################################################################################################
00035 //
00036 //      C L A S S : CConstraintTreeCtrl <<< + CTreeCtrlEx
00037 //
00038 //##############################################################################################################################################
00039 
00040 IMPLEMENT_DYNAMIC(CConstraintTreeCtrl, CTreeCtrlEx)
00041 
00042 CConstraintTreeCtrl::CConstraintTreeCtrl()
00043         : CTreeCtrlEx(), m_eKind( CConstraintTreeCtrl::TK_UNKNOWN )
00044 {
00045 }
00046 
00047 CConstraintTreeCtrl::~CConstraintTreeCtrl()
00048 {
00049 }
00050 
00051 BEGIN_MESSAGE_MAP(CConstraintTreeCtrl, CTreeCtrlEx)
00052         //{{AFX_MSG_MAP(CConstraintTreeCtrl)
00053         ON_WM_LBUTTONDOWN()
00054         ON_WM_RBUTTONDOWN()
00055         ON_WM_KEYUP()
00056         ON_WM_LBUTTONDBLCLK()
00057         //}}AFX_MSG_MAP
00058 END_MESSAGE_MAP()
00059 
00060 //==============================================================================================================================
00061 // PUBLIC METHOD -> SelectAllItems
00062 //
00063 //      DESCRIPTION:
00064 //              Selects or deselects the part of the tree specified by the root item
00065 //      ARGUMENTS:
00066 //              hRoot:
00067 //                      handle of a tree item which is the begining of the selection
00068 //              bSelect:
00069 //                      trivial
00070 //      NOTE:
00071 //              As the base class seems to be a little buggy, we have to select explicitly the first visible item
00072 
00073         void CConstraintTreeCtrl::SelectAllItems( HTREEITEM hRoot, bool bSelect /* = TRUE */ )
00074         {
00075                 for ( HTREEITEM hItem = hRoot ; hItem != NULL ; hItem = GetNextSiblingItem( hItem ) ) {
00076                         for ( HTREEITEM hItem2 = GetChildItem( hItem ) ; hItem2 != NULL ; hItem2 = GetNextSiblingItem( hItem2 ) )
00077                                 SelectAllItems( hItem2, bSelect );
00078                         SetItemState( hItem, ( bSelect ) ? TVIS_SELECTED : 0, TVIS_SELECTED );
00079                 }
00080                 HTREEITEM hItem = GetFirstVisibleItem();
00081                 if ( hItem )
00082                         SelectItemEx( hItem, bSelect );
00083         }
00084 
00085         void CConstraintTreeCtrl::SetKind( CConstraintTreeCtrl::Kind eKind )
00086         {
00087                 m_eKind = eKind;
00088         }
00089 
00090         CConstraintTreeCtrl::Kind CConstraintTreeCtrl::GetKind() const
00091         {
00092                 return m_eKind;
00093         }
00094 
00095         void CConstraintTreeCtrl::SortItemChildren( HTREEITEM hItem )
00096         {
00097                 TVSORTCB tvs;
00098                 tvs.hParent = hItem;
00099                 tvs.lpfnCompare = SpecialCompare;
00100                 tvs.lParam = (LPARAM) this;
00101 
00102                 SortChildrenCB( &tvs );
00103         }
00104 
00105 //==============================================================================================================================
00106 // PROTECTED METHOD -> SendTreeNotification
00107 //
00108 //      DESCRIPTION:
00109 //              Simple helper method in order not to write too much. Sends the specified Tree Notification
00110 //      ARGUMENTS:
00111 //              uiMessage:
00112 //                      id of the message
00113 //              hItem:
00114 //                      handle of the appropriate treeitem
00115 
00116 void CConstraintTreeCtrl::SendTreeNotification( UINT uiMessage, HTREEITEM hItem )
00117 {
00118         CWnd* pWnd = GetParent();
00119         if ( pWnd ) {
00120                 NM_TREEVIEW tv;
00121 
00122                 tv.hdr.hwndFrom = GetSafeHwnd();
00123                 tv.hdr.idFrom = GetWindowLong( GetSafeHwnd(), GWL_ID );
00124                 tv.hdr.code = uiMessage;
00125 
00126                 tv.itemNew.hItem = hItem;
00127                 tv.itemNew.state = GetItemState( hItem, 0xFFFFFFFF );
00128                 tv.itemNew.lParam = GetItemData( hItem );
00129 
00130                 pWnd->SendMessage( WM_NOTIFY, tv.hdr.idFrom, (LPARAM) &tv );
00131         }
00132 }
00133 
00134 //================================================================================================================================
00135 // PROTECTED METHOD -> OnLButtonDown <OVERRIDE, VIRTUAL>
00136 //
00137 //      DESCRIPTION:
00138 //              It catches the click if it was performed on the ItemStateIcon, otherwise call the base class.
00139 //      ARGUMENT:
00140 //              See MSDN.
00141 //      TODO:
00142 //              After catching we should send a NM_CLICK Notification :)
00143 
00144 void CConstraintTreeCtrl::OnLButtonDown( UINT nFlags, CPoint point )
00145 {
00146         UINT flags = 0;
00147         HTREEITEM hItem = HitTest( point, &flags );
00148         if ( hItem && ( flags & TVHT_ONITEMSTATEICON ) ) {
00149                 int iOldState = GETSTATE( hItem );
00150                 if ( iOldState > 2 && iOldState < 8 )
00151                         SendTreeNotification( CTVN_CHECKCHANGED, hItem );
00152         }
00153         CTreeCtrlEx::OnLButtonDown( nFlags, point );
00154 }
00155 
00156 void CConstraintTreeCtrl::OnRButtonDown( UINT nFlags, CPoint point )
00157 {
00158         UINT flags = 0;
00159         HTREEITEM hItem = HitTest( point, &flags );
00160         if ( hItem && ( flags & TVHT_ONITEMSTATEICON ) ) {
00161                 int iOldState = GETSTATE( hItem );
00162                 if ( iOldState > 2 && iOldState < 8 )
00163                         SendTreeNotification( CTVN_CHECKCHANGEDREC, hItem );
00164         }
00165         CTreeCtrlEx::OnRButtonDown( nFlags, point );
00166 }
00167 
00168 //================================================================================================================================
00169 // PROTECTED METHOD -> OnKeyUp <OVERRIDE, VIRTUAL>
00170 //
00171 //      DESCRIPTION:
00172 //              It catches the space key, otherwise call the base class.
00173 //      ARGUMENT:
00174 //              See MSDN.
00175 //      TODO:
00176 //              After catching we should send a NM_KEY Notification :)
00177 
00178 void CConstraintTreeCtrl::OnKeyUp( UINT nChar, UINT nRepCnt, UINT nFlags )
00179 {
00180         if ( nChar == VK_SPACE ) {
00181                 HTREEITEM hItem = GetSelectedItem();
00182                 if ( hItem ) {
00183                         int iOldState = GETSTATE( hItem );
00184                         if ( iOldState > 2 && iOldState < 8 )
00185                                 SendTreeNotification( CTVN_CHECKCHANGED, hItem );
00186                 }
00187                 return;
00188         }
00189         CTreeCtrlEx::OnKeyUp( nChar, nRepCnt, nFlags );
00190 }
00191 
00192 //================================================================================================================================
00193 // PROTECTED METHOD -> OnLButtonDblClk <OVERRIDE, VIRTUAL>
00194 //
00195 //      DESCRIPTION:
00196 //              It catches the double click. If it is on TreeButton the delegate the call to the base class. If it is on either the icon or the label CTVN_SHOWITEM notifcation is sent. In any other case it eats the message.
00197 //      ARGUMENT:
00198 //              See MSDN.
00199 //      TODO:
00200 //              After catching we should send a NM_DBLCLK Notification :)
00201 
00202 void CConstraintTreeCtrl::OnLButtonDblClk(UINT nFlags, CPoint point)
00203 {
00204         UINT flags = 0;
00205         HTREEITEM hItem = HitTest( point, &flags );
00206         if ( hItem )
00207                 if ( flags & TVHT_ONITEMBUTTON )
00208                         CTreeCtrlEx::OnLButtonDblClk(nFlags, point);
00209                 else
00210                         if ( flags & ( TVHT_ONITEMICON | TVHT_ONITEMLABEL ) )
00211                                 SendTreeNotification( CTVN_SHOWITEM, hItem );
00212 }