1898 lines
48 KiB
C++
1898 lines
48 KiB
C++
#include "stdafx.h"
|
|
#include "PropertyListBox.h"
|
|
|
|
#include "InPlaceCtrls.h"
|
|
|
|
|
|
#ifdef _DEBUG
|
|
#define new DEBUG_NEW
|
|
#undef THIS_FILE
|
|
static char THIS_FILE[] = __FILE__;
|
|
#endif
|
|
static unsigned int const CT_IPCEndMsg = RegisterWindowMessage( IPCMSGSTRING );
|
|
|
|
IMPLEMENT_DYNAMIC(CPropertyItem, CObject)
|
|
|
|
CPropertyItem::~CPropertyItem()
|
|
{
|
|
}
|
|
|
|
CPropertyItem::CPropertyItem()
|
|
{
|
|
m_bNameEditable = FALSE;
|
|
m_bValueEditable= TRUE;
|
|
m_eNameStyle = EDT_NONE;
|
|
m_eValueStyle = EDT_NONE;
|
|
m_sName = _T("");
|
|
m_sValue = _T("");
|
|
m_sFileFilter = _T("");
|
|
m_pNameStrList = NULL;
|
|
m_pValueStrList = NULL;
|
|
|
|
m_dwUserData = 0;
|
|
m_dwUserDataEx = 0;
|
|
}
|
|
|
|
CPropertyItem::CPropertyItem(CString sName,
|
|
CString sValue,
|
|
ItemStyle nStyle,
|
|
BOOL bNameEditable,
|
|
BOOL bValueEditable,
|
|
CStringList* pStrList,
|
|
CString sFileFilter)
|
|
{
|
|
m_bNameEditable = bNameEditable;
|
|
m_bValueEditable= bValueEditable;
|
|
m_eNameStyle = EDT_NONE;
|
|
m_eValueStyle = nStyle;
|
|
m_sName = sName;
|
|
m_sValue = sValue;
|
|
m_sFileFilter = sFileFilter;
|
|
m_pNameStrList = NULL;
|
|
m_pValueStrList = pStrList;
|
|
|
|
m_dwUserData = 0;
|
|
m_dwUserDataEx = 0;
|
|
}
|
|
|
|
CPropertyItem& CPropertyItem::operator = (const CPropertyItem& item)
|
|
{
|
|
m_bNameEditable = item.m_bNameEditable;
|
|
m_bValueEditable= item.m_bValueEditable;
|
|
m_eNameStyle = item.m_eNameStyle;
|
|
m_eValueStyle = item.m_eValueStyle;
|
|
m_sName = item.m_sName;
|
|
m_sValue = item.m_sValue;
|
|
m_sFileFilter = item.m_sFileFilter;
|
|
m_pNameStrList = item.m_pNameStrList;
|
|
m_pValueStrList = item.m_pValueStrList;
|
|
|
|
m_dwUserData = item.m_dwUserData;
|
|
m_dwUserDataEx = item.m_dwUserDataEx;
|
|
|
|
return *this;
|
|
}
|
|
|
|
/////////////////////////////////////////////////////////////////////////////
|
|
// CPropertyItemTab
|
|
IMPLEMENT_DYNAMIC(CPropertyItemTab, CObject)
|
|
|
|
CPropertyItemTab::~CPropertyItemTab()
|
|
{
|
|
while(m_listItem.GetCount() > 0) delete m_listItem.RemoveHead();
|
|
}
|
|
|
|
CPropertyItemTab::CPropertyItemTab()
|
|
{
|
|
m_bNameEditable = FALSE;
|
|
m_bValueEditable= FALSE;
|
|
m_eNameStyle = EDT_NONE;
|
|
m_eValueStyle = EDT_NONE;
|
|
m_sName = _T("");
|
|
m_sValue = _T("");
|
|
m_sFileFilter = _T("");
|
|
m_pNameStrList = NULL;
|
|
m_pValueStrList = NULL;
|
|
|
|
m_bExpand = FALSE;
|
|
m_listItem.RemoveAll();
|
|
|
|
m_dwUserParam = 0;
|
|
}
|
|
|
|
CPropertyItemTab::CPropertyItemTab(CString sName,
|
|
BOOL bExpand,
|
|
CString sValue,
|
|
ItemStyle nStyle,
|
|
BOOL bNameEditable,
|
|
BOOL bValueEditable,
|
|
CStringList* pStrList,
|
|
CString sFileFilter)
|
|
{
|
|
m_bNameEditable = bNameEditable;
|
|
m_bValueEditable= bValueEditable;
|
|
m_eNameStyle = EDT_NONE;
|
|
m_eValueStyle = nStyle;
|
|
m_sName = sName;
|
|
m_sValue = sValue;
|
|
m_sFileFilter = sFileFilter;
|
|
m_pNameStrList = NULL;
|
|
m_pValueStrList = pStrList;
|
|
|
|
m_bExpand = bExpand;
|
|
m_listItem.RemoveAll();
|
|
|
|
m_dwUserParam = 0;
|
|
}
|
|
|
|
CPropertyItemTab::CPropertyItemTab(CPropertyItem& item, BOOL bExpand)
|
|
{
|
|
m_bNameEditable = item.m_bNameEditable;
|
|
m_bValueEditable= item.m_bValueEditable;
|
|
m_eNameStyle = item.m_eNameStyle;
|
|
m_eValueStyle = item.m_eValueStyle;
|
|
m_sName = item.m_sName;
|
|
m_sValue = item.m_sValue;
|
|
m_sFileFilter = item.m_sFileFilter;
|
|
m_pNameStrList = item.m_pNameStrList;
|
|
m_pValueStrList = item.m_pValueStrList;
|
|
|
|
m_bExpand = bExpand;
|
|
m_listItem.RemoveAll();
|
|
|
|
m_dwUserParam = 0;
|
|
}
|
|
|
|
CPropertyItemTab& CPropertyItemTab::operator = (const CPropertyItemTab& tab)
|
|
{
|
|
m_bNameEditable = tab.m_bNameEditable;
|
|
m_bValueEditable= tab.m_bValueEditable;
|
|
m_eNameStyle = tab.m_eNameStyle;
|
|
m_eValueStyle = tab.m_eValueStyle;
|
|
m_sName = tab.m_sName;
|
|
m_sValue = tab.m_sValue;
|
|
m_sFileFilter = tab.m_sFileFilter;
|
|
m_pNameStrList = tab.m_pNameStrList;
|
|
m_pValueStrList = tab.m_pValueStrList;
|
|
|
|
m_bExpand = tab.m_bExpand;
|
|
while(m_listItem.GetCount() > 0) delete m_listItem.RemoveHead();
|
|
|
|
POSITION pos = tab.m_listItem.GetHeadPosition();
|
|
CPropertyItem *pItem, *pNewItem;
|
|
while(pos != NULL)
|
|
{
|
|
pItem = (CPropertyItem*)tab.m_listItem.GetNext(pos);
|
|
pNewItem = new CPropertyItem();
|
|
(*pNewItem) = (*pItem);
|
|
m_listItem.AddTail(pNewItem);
|
|
}
|
|
|
|
m_dwUserParam = tab.m_dwUserParam;
|
|
|
|
return *this;
|
|
}
|
|
|
|
|
|
/////////////////////////////////////////////////////////////////////////////
|
|
// CPropertyListBox
|
|
IMPLEMENT_DYNAMIC(CPropertyListBox, CListBox)
|
|
|
|
CPropertyListBox::CPropertyListBox()
|
|
{
|
|
m_bEditName = FALSE;
|
|
m_bSeperate = FALSE;
|
|
m_nLeftBorder = 16;
|
|
m_nNameWidth = 60;
|
|
m_iCurSel = -1;
|
|
m_pWndCtrl = NULL;
|
|
m_pWndButton = NULL;
|
|
m_pWndSpin = NULL;
|
|
m_listItemTab.RemoveAll();
|
|
}
|
|
|
|
CPropertyListBox::~CPropertyListBox()
|
|
{
|
|
if(m_pWndCtrl != NULL) delete m_pWndCtrl;
|
|
if(m_pWndButton != NULL) delete m_pWndButton;
|
|
if(m_pWndSpin != NULL) delete m_pWndSpin;
|
|
|
|
while(m_listItemTab.GetCount() > 0) delete m_listItemTab.RemoveHead();
|
|
}
|
|
|
|
BEGIN_MESSAGE_MAP(CPropertyListBox, CListBox)
|
|
//{{AFX_MSG_MAP(CPropertyListBox)
|
|
ON_WM_LBUTTONDBLCLK()
|
|
ON_WM_SIZE()
|
|
ON_CONTROL_REFLECT(LBN_SELCHANGE, OnSelchange)
|
|
ON_WM_LBUTTONDOWN()
|
|
ON_WM_KEYDOWN()
|
|
ON_WM_MOUSEMOVE()
|
|
ON_REGISTERED_MESSAGE( CT_IPCEndMsg, OnChildKillFoucs )
|
|
ON_WM_VSCROLL()
|
|
ON_WM_SETCURSOR()
|
|
ON_WM_LBUTTONUP()
|
|
ON_WM_CAPTURECHANGED()
|
|
ON_WM_NCLBUTTONDOWN()
|
|
ON_WM_MOUSEWHEEL()
|
|
//}}AFX_MSG_MAP
|
|
ON_MESSAGE(WM_USER_CHILDVALUECHANGED, OnChildCtrlValueChanged)
|
|
END_MESSAGE_MAP()
|
|
|
|
/////////////////////////////////////////////////////////////////////////////
|
|
// CPropertyListBox virtual function handlers
|
|
|
|
void CPropertyListBox::DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct)
|
|
{
|
|
if(GetCount() <= 0) return;
|
|
|
|
CDC dc;
|
|
dc.Attach(lpDrawItemStruct->hDC);
|
|
|
|
CPen pen(PS_SOLID, 1, ::GetSysColor(COLOR_BTNFACE));
|
|
CPen* pOldPen = dc.SelectObject(&pen);
|
|
|
|
CRect rect;
|
|
if(m_nLeftBorder > 0)
|
|
{
|
|
GetClientRect(rect);
|
|
rect.left += m_nLeftBorder;
|
|
dc.MoveTo(rect.TopLeft());
|
|
dc.LineTo(rect.left, rect.bottom);
|
|
}
|
|
|
|
rect = lpDrawItemStruct->rcItem;
|
|
rect.left += m_nLeftBorder;
|
|
rect.bottom--;
|
|
dc.MoveTo(rect.left, rect.bottom);
|
|
dc.LineTo(rect.BottomRight());
|
|
|
|
int iRight = rect.left + m_nNameWidth;
|
|
dc.MoveTo(iRight, rect.top);
|
|
dc.LineTo(iRight, rect.bottom);
|
|
|
|
int iIndex = lpDrawItemStruct->itemID;
|
|
if(iIndex < 0) return; // 判断当前pItem数据是否有效
|
|
CPropertyItem* pItem = (CPropertyItem*)lpDrawItemStruct->itemData;
|
|
BOOL bCategory = pItem->IsKindOf(RUNTIME_CLASS(CPropertyItemTab));
|
|
|
|
dc.SelectStockObject(BLACK_PEN);
|
|
if(m_nLeftBorder > 0 && bCategory)
|
|
{
|
|
CPoint ptCenter(m_nLeftBorder / 2, (rect.top + rect.bottom) / 2);
|
|
CRect rcSign(CPoint(ptCenter.x - 4, ptCenter.y -4), CSize(9, 9));
|
|
dc.FillRect(rcSign, CBrush::FromHandle((HBRUSH)GetStockObject(WHITE_BRUSH)));
|
|
dc.FrameRect(rcSign, CBrush::FromHandle((HBRUSH)GetStockObject(BLACK_BRUSH)));
|
|
// minus
|
|
dc.MoveTo(ptCenter.x - 2, ptCenter.y);
|
|
dc.LineTo(ptCenter.x + 3, ptCenter.y);
|
|
// plus
|
|
if(!((CPropertyItemTab*)pItem)->m_bExpand)
|
|
{
|
|
dc.MoveTo(ptCenter.x, ptCenter.y - 2);
|
|
dc.LineTo(ptCenter.x, ptCenter.y + 3);
|
|
}
|
|
}
|
|
dc.SelectObject(pOldPen);
|
|
|
|
COLORREF crOldTextColor = dc.GetTextColor();
|
|
COLORREF crOldBkColor = dc.GetBkColor();
|
|
CRect rcValue = GetItemValueRect(rect);
|
|
|
|
BOOL bSelected = (lpDrawItemStruct->itemState & ODS_SELECTED);
|
|
if(!bSelected || m_bEditName || m_pWndCtrl != NULL && !m_pWndCtrl->IsWindowVisible()
|
|
|| !pItem->m_bValueEditable || pItem->m_eValueStyle == CPropertyItem::BTN_NONE)
|
|
{
|
|
rcValue.DeflateRect(3, 1, 2, 0);
|
|
if(!pItem->m_bValueEditable)
|
|
{
|
|
dc.SetTextColor(::GetSysColor(COLOR_GRAYTEXT));
|
|
dc.DrawText(pItem->m_sValue, rcValue, DT_SINGLELINE|DT_VCENTER);
|
|
dc.SetTextColor(crOldTextColor);
|
|
}
|
|
else dc.DrawText(pItem->m_sValue, rcValue, DT_SINGLELINE|DT_VCENTER);
|
|
}
|
|
|
|
if(bSelected && !m_bEditName)
|
|
{
|
|
dc.SetTextColor(::GetSysColor(COLOR_HIGHLIGHTTEXT));
|
|
CWnd* pWnd = GetFocus();
|
|
if(pWnd == this || IsChild(pWnd)) dc.SetBkColor(::GetSysColor(COLOR_HIGHLIGHT));
|
|
else dc.SetBkColor(::GetSysColor(COLOR_GRAYTEXT));
|
|
}
|
|
|
|
dc.ExtTextOut(rect.left, rect.top, ETO_OPAQUE, rect, _T(""), 0, NULL);
|
|
if (m_bEditName && NULL != m_pWndCtrl)
|
|
m_pWndCtrl->Invalidate();
|
|
|
|
if (!bSelected || !m_bEditName || pItem->m_eValueStyle == CPropertyItem::BTN_NONE)
|
|
{
|
|
rect.DeflateRect(3, 1, 2, 0);
|
|
CFont fontLabel;
|
|
CFont* pOldFont = NULL;
|
|
if(bCategory)
|
|
{
|
|
LOGFONT logFont;
|
|
CFont* pFont = GetFont();
|
|
pFont->GetLogFont(&logFont);
|
|
logFont.lfWeight = FW_BOLD;
|
|
fontLabel.CreateFontIndirect(&logFont);
|
|
pOldFont = dc.SelectObject(&fontLabel);
|
|
}
|
|
|
|
dc.DrawText(pItem->m_sName, rect, DT_SINGLELINE|DT_VCENTER);
|
|
if(pOldFont != NULL) dc.SelectObject(pOldFont);
|
|
}
|
|
|
|
dc.SetTextColor(crOldTextColor);
|
|
dc.SetBkColor(crOldBkColor);
|
|
|
|
dc.Detach();
|
|
}
|
|
|
|
/////////////////////////////////////////////////////////////////////////////
|
|
// CPropertyListBox private function handlers
|
|
|
|
CRect CPropertyListBox::GetItemValueRect(CRect& rect)
|
|
{
|
|
CRect rcValue = rect;
|
|
rect.right -= rect.Width() - m_nNameWidth;
|
|
rect.left++;
|
|
rcValue.left += m_nNameWidth;
|
|
return rcValue;
|
|
}
|
|
|
|
void CPropertyListBox::CreatSpinCtrl(CRect rect)
|
|
{
|
|
if (rect.Width() > rect.Height() + 4) rect.left = rect.right - rect.Height();
|
|
else
|
|
{
|
|
rect.left += 4;
|
|
rect.right = rect.left + rect.Height();
|
|
}
|
|
|
|
rect.InflateRect(0, 1, 0, 1);
|
|
if(m_pWndSpin != NULL)
|
|
{
|
|
m_pWndSpin->SetWindowPos(NULL, rect.left, rect.top, rect.Width(), rect.Height(), SWP_NOZORDER|SWP_SHOWWINDOW);
|
|
return;
|
|
}
|
|
|
|
if(m_pWndSpin != NULL) delete m_pWndSpin;
|
|
m_pWndSpin = new CSpinButtonCtrl();
|
|
m_pWndSpin->Create(WS_VISIBLE|WS_CHILD|UDS_SETBUDDYINT|UDS_ARROWKEYS|UDS_NOTHOUSANDS, rect, this, 0);
|
|
m_pWndSpin->SetRange32(UD_MINVAL, UD_MAXVAL);
|
|
}
|
|
|
|
void CPropertyListBox::MoveCtrl(CPropertyItem*& pItem, CRect rect)
|
|
{
|
|
if(m_pWndSpin != NULL) m_pWndSpin->SetBuddy(NULL);
|
|
|
|
if(m_bEditName)
|
|
{
|
|
MoveCtrl(pItem, rect, TRUE);
|
|
m_pWndCtrl->SetFocus();
|
|
return;
|
|
}
|
|
if(!pItem->m_bValueEditable) {HideCtrl(); return;}
|
|
MoveCtrl(pItem, rect, FALSE);
|
|
m_pWndCtrl->SetFocus();
|
|
}
|
|
|
|
void CPropertyListBox::MoveCtrl(CPropertyItem*& pItem, CRect& rect, BOOL bName)
|
|
{
|
|
CString sText = pItem->m_sValue;
|
|
CStringList*& pStrList = pItem->m_pValueStrList;
|
|
CPropertyItem::ItemStyle eStyle = pItem->m_eValueStyle;
|
|
if (bName)
|
|
{
|
|
sText = pItem->m_sName;
|
|
pStrList = pItem->m_pNameStrList;
|
|
eStyle = pItem->m_eNameStyle;
|
|
}
|
|
|
|
switch(eStyle)
|
|
{
|
|
case CPropertyItem::EDT_NONE:
|
|
if(m_pWndButton != NULL) m_pWndButton->ShowWindow(SW_HIDE);
|
|
if(m_pWndSpin != NULL) m_pWndSpin->ShowWindow(SW_HIDE);
|
|
CInPlaceEdit::CreateCtrl1(m_pWndCtrl, rect, this, sText, FALSE);
|
|
break;
|
|
case CPropertyItem::EDT_NUM:
|
|
if(m_pWndButton != NULL) m_pWndButton->ShowWindow(SW_HIDE);
|
|
if(m_pWndSpin != NULL) m_pWndSpin->ShowWindow(SW_HIDE);
|
|
CInPlaceEdit::CreateCtrl1(m_pWndCtrl, rect, this, sText, TRUE);
|
|
break;
|
|
case CPropertyItem::EDT_REAL:
|
|
if(m_pWndButton != NULL) m_pWndButton->ShowWindow(SW_HIDE);
|
|
if(m_pWndSpin != NULL) m_pWndSpin->ShowWindow(SW_HIDE);
|
|
CInPlaceEdit::CreateCtrl1(m_pWndCtrl, rect, this, sText, FALSE, TRUE);
|
|
break;
|
|
case CPropertyItem::EDT_SPIN:
|
|
if(m_pWndButton != NULL) m_pWndButton->ShowWindow(SW_HIDE);
|
|
CreatSpinCtrl(rect);
|
|
rect.right -= rect.Height();
|
|
CInPlaceEdit::CreateCtrl1(m_pWndCtrl, rect, this, sText, TRUE);
|
|
m_pWndSpin->SetBuddy(m_pWndCtrl);
|
|
break;
|
|
case CPropertyItem::CMB_LIST_YESNO:
|
|
{
|
|
CStringList list;
|
|
list.AddTail(_T("是"));
|
|
list.AddTail(_T("否"));
|
|
if(m_pWndButton != NULL) m_pWndButton->ShowWindow(SW_HIDE);
|
|
if(m_pWndSpin != NULL) m_pWndSpin->ShowWindow(SW_HIDE);
|
|
CInPlaceComboBox::CreateCtrl1(m_pWndCtrl, rect, this, sText, &list, 100, TRUE);
|
|
}
|
|
break;
|
|
case CPropertyItem::CMB_LIST:
|
|
if(m_pWndButton != NULL) m_pWndButton->ShowWindow(SW_HIDE);
|
|
if(m_pWndSpin != NULL) m_pWndSpin->ShowWindow(SW_HIDE);
|
|
if(pStrList == NULL) pStrList = pItem->OnComboAskStringList(bName);
|
|
CInPlaceComboBox::CreateCtrl1(m_pWndCtrl, rect, this, sText, pStrList, 300, TRUE);
|
|
break;
|
|
case CPropertyItem::CMB_DOWN:
|
|
if(m_pWndButton != NULL) m_pWndButton->ShowWindow(SW_HIDE);
|
|
if(m_pWndSpin != NULL) m_pWndSpin->ShowWindow(SW_HIDE);
|
|
if(pStrList == NULL) pStrList = pItem->OnComboAskStringList(bName);
|
|
CInPlaceComboBox::CreateCtrl1(m_pWndCtrl, rect, this, sText, pStrList, 300, FALSE);
|
|
break;
|
|
case CPropertyItem::BTN_EDIT:
|
|
case CPropertyItem::BTN_EDIT_SELFILE:
|
|
case CPropertyItem::BTN_EDIT_SELPATH:
|
|
if(m_pWndSpin != NULL) m_pWndSpin->ShowWindow(SW_HIDE);
|
|
CInPlaceButton::CreateCtrl1(m_pWndButton, rect, this);
|
|
rect.right -= (rect.Height()+1);
|
|
CInPlaceEdit::CreateCtrl1(m_pWndCtrl, rect, this, sText, FALSE);
|
|
break;
|
|
case CPropertyItem::BTN_NONE:
|
|
if(m_pWndCtrl != NULL) m_pWndCtrl->ShowWindow(SW_HIDE);
|
|
if(m_pWndSpin != NULL) m_pWndSpin->ShowWindow(SW_HIDE);
|
|
CInPlaceButton::CreateCtrl1(m_pWndButton, rect, this);
|
|
break;
|
|
default:
|
|
HideCtrl();
|
|
return;
|
|
}
|
|
}
|
|
|
|
/////////////////////////////////////////////////////////////////////////////
|
|
// CPropertyListBox message handlers
|
|
|
|
void CPropertyListBox::OnSelchange()
|
|
{
|
|
int iCurSel = CListBox::GetCurSel();
|
|
if(iCurSel < 0) return;
|
|
|
|
CRect rect, rcValue;
|
|
GetItemRect(iCurSel, rect);
|
|
rect.left += m_nLeftBorder;
|
|
rect.bottom--;
|
|
rcValue = GetItemValueRect(rect);
|
|
|
|
CPropertyItem* pItem = (CPropertyItem*)GetItemData(iCurSel);
|
|
if(m_iCurSel == iCurSel && !m_bEditName && pItem->m_bNameEditable
|
|
&& (!pItem->m_bValueEditable || m_pWndCtrl != NULL && m_pWndCtrl->IsWindowVisible()))
|
|
{
|
|
m_bEditName = TRUE;
|
|
MoveCtrl(pItem, rect);
|
|
}
|
|
else
|
|
{
|
|
if(m_bEditName)
|
|
{
|
|
m_bEditName = FALSE;
|
|
InvalidateRect(rect);
|
|
GetParent()->SendMessage(WM_USER_CHILDVALUECHANGED, MAKEWPARAM(3, MAKEWORD(0, m_bEditName)), (LPARAM)m_hWnd);
|
|
}
|
|
m_iCurSel = iCurSel;
|
|
MoveCtrl(pItem, rcValue);
|
|
}
|
|
GetParent()->SendMessage(WM_USER_CHILDVALUECHANGED, MAKEWPARAM(4, MAKEWORD(0, m_bEditName)), (LPARAM)m_hWnd);
|
|
}
|
|
|
|
void CPropertyListBox::OnNcLButtonDown(UINT nHitTest, CPoint point)
|
|
{
|
|
HideCtrl();
|
|
|
|
CListBox::OnNcLButtonDown(nHitTest, point);
|
|
}
|
|
|
|
BOOL CPropertyListBox::OnMouseWheel(UINT nFlags, short zDelta, CPoint pt)
|
|
{
|
|
HideCtrl();
|
|
|
|
return CListBox::OnMouseWheel(nFlags, zDelta, pt);
|
|
}
|
|
|
|
void CPropertyListBox::OnLButtonDown(UINT nFlags, CPoint point)
|
|
{
|
|
if (IsHitOnSeperator(&m_rcSeperator))
|
|
{
|
|
StartTracking();
|
|
return;
|
|
}
|
|
|
|
CListBox::OnLButtonDown(nFlags, point);
|
|
|
|
int iCurSel = CListBox::GetCurSel();
|
|
if(iCurSel < 0) return;
|
|
CRect rect;
|
|
GetItemRect(iCurSel, rect);
|
|
rect.right = rect.left + m_nLeftBorder;
|
|
if(rect.PtInRect(point))
|
|
{
|
|
CPropertyItem* pItem = (CPropertyItem*)GetItemData(iCurSel);
|
|
DoCollapseExpand(pItem);
|
|
InvalidateRect(rect);
|
|
}
|
|
}
|
|
|
|
void CPropertyListBox::OnLButtonDblClk(UINT nFlags, CPoint point)
|
|
{
|
|
CListBox::OnLButtonDblClk(nFlags, point);
|
|
|
|
int iCurSel = CListBox::GetCurSel();
|
|
if(iCurSel < 0) return;
|
|
CRect rect;
|
|
GetItemRect(iCurSel, rect);
|
|
if(rect.PtInRect(point))
|
|
{
|
|
CPropertyItem* pItem = (CPropertyItem*)GetItemData(iCurSel);
|
|
DoCollapseExpand(pItem);
|
|
rect.right = rect.left + m_nLeftBorder;
|
|
InvalidateRect(rect);
|
|
}
|
|
if(m_pWndCtrl != NULL && m_pWndCtrl->IsWindowVisible()) m_pWndCtrl->SetFocus();
|
|
}
|
|
|
|
void CPropertyListBox::OnSize(UINT nType, int cx, int cy)
|
|
{
|
|
CListBox::OnSize(nType, cx, cy);
|
|
UpdateCtrl();
|
|
}
|
|
|
|
void CPropertyListBox::OnKeyDown(UINT nChar, UINT nRepCnt, UINT nFlags)
|
|
{
|
|
int iCurSel = CListBox::GetCurSel();
|
|
if(iCurSel < 0) return;
|
|
CRect rect;
|
|
GetItemRect(iCurSel, rect);
|
|
rect.right = rect.left + m_nLeftBorder;
|
|
CPropertyItem* pItem = (CPropertyItem*)GetItemData(iCurSel);
|
|
if(pItem->IsKindOf(RUNTIME_CLASS(CPropertyItemTab)))
|
|
{
|
|
CPropertyItemTab* pTab = (CPropertyItemTab*)pItem;
|
|
switch(nChar)
|
|
{
|
|
case VK_RIGHT:
|
|
case VK_ADD:
|
|
if(pTab->m_bExpand) break;
|
|
ExpandTab(pTab);
|
|
InvalidateRect(rect);
|
|
return;
|
|
case VK_LEFT:
|
|
case VK_SUBTRACT:
|
|
if(!pTab->m_bExpand) break;
|
|
CollapseTab(pTab);
|
|
InvalidateRect(rect);
|
|
return;
|
|
}
|
|
}
|
|
if(nChar == VK_RIGHT && m_pWndCtrl != NULL && m_pWndCtrl->IsWindowVisible())
|
|
{
|
|
m_pWndCtrl->SetFocus();
|
|
return;
|
|
}
|
|
|
|
CListBox::OnKeyDown(nChar, nRepCnt, nFlags);
|
|
}
|
|
|
|
LRESULT CPropertyListBox::OnChildCtrlValueChanged(WPARAM wParam, LPARAM lParam)
|
|
{
|
|
int iCurSel = CListBox::GetCurSel();
|
|
if(iCurSel < 0)
|
|
return 0l;
|
|
|
|
CPropertyItem* pItem = (CPropertyItem*)GetItemData(iCurSel);
|
|
|
|
CString sText;
|
|
switch(wParam)
|
|
{
|
|
case 0: //Edit action
|
|
if( !m_pWndCtrl || !IsWindow(m_pWndCtrl->m_hWnd))
|
|
return 0l;
|
|
if (lParam == 1)
|
|
break;
|
|
m_pWndCtrl->GetWindowText(sText);
|
|
if(m_bEditName)
|
|
{
|
|
if (pItem->m_sName == sText)
|
|
return 0l;
|
|
pItem->m_sName = sText;
|
|
}
|
|
else if(pItem->m_bValueEditable)
|
|
{
|
|
if (pItem->m_sValue == sText)
|
|
return 0l;
|
|
pItem->m_sValue = sText;
|
|
}
|
|
|
|
pItem->OnEditCtrlChange();
|
|
break;
|
|
case 1: //Combo box action
|
|
m_pWndCtrl->GetWindowText(sText);
|
|
if(m_bEditName)
|
|
{
|
|
if (pItem->m_sName == sText)
|
|
return 0l;
|
|
pItem->m_sName = sText;
|
|
}
|
|
else if(pItem->m_bValueEditable)
|
|
{
|
|
if (pItem->m_sValue == sText)
|
|
return 0l;
|
|
pItem->m_sValue = sText;
|
|
}
|
|
|
|
if(lParam == 1) pItem->OnComboSelectChange();
|
|
else pItem->OnComboEditChange();
|
|
break;
|
|
case 2: //Button action
|
|
switch(pItem->m_eValueStyle)
|
|
{
|
|
case CPropertyItem::BTN_EDIT:
|
|
case CPropertyItem::BTN_NONE:
|
|
pItem->OnButtonClicked();
|
|
break;
|
|
case CPropertyItem::BTN_EDIT_SELFILE:
|
|
{
|
|
CString sFilter = pItem->m_sFileFilter;
|
|
if(sFilter.IsEmpty()) sFilter = _T("All files (*.*)|*.*|");
|
|
if(sFilter.Find('|') < 0) sFilter.Format(_T("File type(*.%s)|*.%s|"), sFilter, sFilter);
|
|
CFileDialog dlg(TRUE, NULL, pItem->m_sValue, OFN_HIDEREADONLY, sFilter);
|
|
if(dlg.DoModal() == IDOK)
|
|
{
|
|
if (pItem->m_sValue == dlg.GetPathName())
|
|
return 0l;
|
|
pItem->m_sValue = dlg.GetPathName();
|
|
if(m_pWndCtrl != NULL) m_pWndCtrl->SetWindowText(pItem->m_sValue);
|
|
}
|
|
}
|
|
break;
|
|
case CPropertyItem::BTN_EDIT_SELPATH:
|
|
{
|
|
LPMALLOC pMalloc;
|
|
if(SHGetMalloc(&pMalloc) != NOERROR) return 0l;
|
|
BROWSEINFO bInfo;
|
|
LPITEMIDLIST pidl;
|
|
bInfo.hwndOwner = m_hWnd;
|
|
bInfo.pidlRoot = NULL;
|
|
bInfo.pszDisplayName = pItem->m_sValue.GetBuffer(MAX_PATH);
|
|
bInfo.lpszTitle = _T("");
|
|
bInfo.ulFlags = BIF_RETURNFSANCESTORS | BIF_RETURNONLYFSDIRS;
|
|
bInfo.lpfn = NULL;
|
|
pidl = SHBrowseForFolder(&bInfo);
|
|
pItem->m_sValue.ReleaseBuffer();
|
|
if(pidl == NULL) return 0l;
|
|
SHGetPathFromIDList(pidl, sText.GetBuffer(MAX_PATH));
|
|
sText.ReleaseBuffer();
|
|
pMalloc->Free(pidl);
|
|
pMalloc->Release();
|
|
|
|
if (pItem->m_sValue == sText)
|
|
return 0l;
|
|
pItem->m_sValue = sText;
|
|
if(m_pWndCtrl != NULL) m_pWndCtrl->SetWindowText(pItem->m_sValue);
|
|
}
|
|
break;
|
|
}
|
|
}
|
|
|
|
GetParent()->SendMessage(WM_USER_CHILDVALUECHANGED, MAKEWPARAM(wParam, MAKEWORD(lParam, m_bEditName)), (LPARAM)m_hWnd);
|
|
|
|
return 0l;
|
|
}
|
|
|
|
/////////////////////////////////////////////////////////////////////////////
|
|
// CPropertyListBox user interface function handlers
|
|
|
|
void CPropertyListBox::EditName()
|
|
{
|
|
int iCurSel = CListBox::GetCurSel();
|
|
if(iCurSel < 0) return;
|
|
|
|
CRect rect;
|
|
GetItemRect(iCurSel, rect);
|
|
rect.left += m_nLeftBorder;
|
|
rect.bottom--;
|
|
GetItemValueRect(rect);
|
|
|
|
CPropertyItem* pItem = (CPropertyItem*)GetItemData(iCurSel);
|
|
if(pItem->m_bNameEditable)
|
|
{
|
|
m_bEditName = TRUE;
|
|
InvalidateRect(rect);
|
|
MoveCtrl(pItem, rect);
|
|
}
|
|
}
|
|
|
|
void CPropertyListBox::ResetContent()
|
|
{
|
|
CListBox::ResetContent();
|
|
HideCtrl();
|
|
m_iCurSel = -1;
|
|
while(m_listItemTab.GetCount() > 0) delete m_listItemTab.RemoveHead();
|
|
}
|
|
|
|
void CPropertyListBox::Reflash()
|
|
{
|
|
CListBox::ResetContent();
|
|
HideCtrl();
|
|
CPropertyItemTab* pTab;
|
|
POSITION pos = m_listItemTab.GetHeadPosition();
|
|
while(pos != NULL)
|
|
{
|
|
pTab = (CPropertyItemTab*)m_listItemTab.GetNext(pos);
|
|
CListBox::AddString((LPCTSTR)pTab);
|
|
if(pTab->m_bExpand)
|
|
{
|
|
pTab->m_bExpand = FALSE;
|
|
ExpandTab(pTab);
|
|
}
|
|
}
|
|
}
|
|
|
|
void CPropertyListBox::UpdateCtrl()
|
|
{
|
|
HideCtrl();
|
|
int iCurSel = CListBox::GetCurSel();
|
|
if(iCurSel < 0) return;
|
|
if(m_pWndCtrl != NULL)
|
|
{
|
|
delete m_pWndCtrl;
|
|
m_pWndCtrl = NULL;
|
|
}
|
|
CRect rect;
|
|
GetItemRect(iCurSel, rect);
|
|
rect.left += m_nLeftBorder;
|
|
rect.bottom--;
|
|
|
|
m_bEditName = FALSE;
|
|
CPropertyItem* pItem = (CPropertyItem*)GetItemData(iCurSel);
|
|
MoveCtrl(pItem, GetItemValueRect(rect));
|
|
}
|
|
|
|
CWnd* CPropertyListBox::GetSubCtrl()
|
|
{
|
|
return m_pWndCtrl;
|
|
}
|
|
|
|
UINT CPropertyListBox::SetLeftBorder(UINT nSize)
|
|
{
|
|
m_nLeftBorder = nSize;
|
|
if(m_nLeftBorder < 10) m_nLeftBorder = 10;
|
|
return m_nLeftBorder;
|
|
}
|
|
|
|
UINT CPropertyListBox::GetLeftBorder()
|
|
{
|
|
return m_nLeftBorder;
|
|
}
|
|
|
|
UINT CPropertyListBox::SetNameWidth(UINT nWidth)
|
|
{
|
|
m_nNameWidth = nWidth;
|
|
if(m_nNameWidth < 10) m_nNameWidth = 10;
|
|
return m_nNameWidth;
|
|
}
|
|
|
|
UINT CPropertyListBox::GetNameWidth()
|
|
{
|
|
return m_nNameWidth;
|
|
}
|
|
|
|
UINT CPropertyListBox::GetTabCount()
|
|
{
|
|
return m_listItemTab.GetCount();
|
|
}
|
|
|
|
UINT CPropertyListBox::GetTotalItemCount()
|
|
{
|
|
UINT nCount = 0;
|
|
CPropertyItemTab* pTab;
|
|
POSITION pos = m_listItemTab.GetHeadPosition();
|
|
while(pos != NULL)
|
|
{
|
|
pTab = (CPropertyItemTab*)m_listItemTab.GetNext(pos);
|
|
nCount += pTab->m_listItem.GetCount();
|
|
}
|
|
return nCount;
|
|
}
|
|
|
|
UINT CPropertyListBox::GetItemCount(UINT nTabIndex)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
FindTab(pTab, nTabIndex);
|
|
if(pTab == NULL) return 0;
|
|
else return pTab->m_listItem.GetCount();
|
|
}
|
|
|
|
UINT CPropertyListBox::GetItemCount(CString sTabName)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
FindTab(pTab, sTabName);
|
|
if(pTab == NULL) return 0;
|
|
else return pTab->m_listItem.GetCount();
|
|
}
|
|
|
|
UINT CPropertyListBox::GetItemCount(CPropertyItemTab*& pTab)
|
|
{
|
|
return pTab->m_listItem.GetCount();
|
|
}
|
|
|
|
CPropertyItemTab* CPropertyListBox::AddTab(CString sName, BOOL bExpand, BOOL bNameEditable,
|
|
CString sValue, CPropertyItem::ItemStyle nStyle, BOOL bValueEditable)
|
|
{
|
|
CPropertyItemTab* pTab = new CPropertyItemTab(sName, bExpand, sValue, nStyle,
|
|
bNameEditable, bValueEditable);
|
|
CListBox::AddString(LPCTSTR(pTab));
|
|
m_listItemTab.AddTail(pTab);
|
|
return pTab;
|
|
}
|
|
|
|
CPropertyItemTab* CPropertyListBox::AddTab(CPropertyItem& item, BOOL bExpand)
|
|
{
|
|
CPropertyItemTab* pTab = new CPropertyItemTab(item, bExpand);
|
|
CListBox::AddString(LPCTSTR(pTab));
|
|
m_listItemTab.AddTail(pTab);
|
|
return pTab;
|
|
}
|
|
|
|
CPropertyItemTab* CPropertyListBox::AddTab(CPropertyItemTab& tab)
|
|
{
|
|
CPropertyItemTab* pTab = new CPropertyItemTab();
|
|
*pTab = tab;
|
|
CListBox::AddString(LPCTSTR(pTab));
|
|
m_listItemTab.AddTail(pTab);
|
|
if(pTab->m_bExpand) ExpandTab(pTab);
|
|
return pTab;
|
|
}
|
|
|
|
BOOL CPropertyListBox::DeleteTab(UINT nTabIndex)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
POSITION pos = FindTab(pTab, nTabIndex);
|
|
if(pTab == NULL) return FALSE;
|
|
m_listItemTab.RemoveAt(pos);
|
|
|
|
int iIndex = FindString(-1, (LPCTSTR)pTab);
|
|
if(iIndex >= 0)
|
|
{
|
|
CollapseTab(pTab);
|
|
CListBox::DeleteString(iIndex);
|
|
CListBox::SetCurSel(iIndex);
|
|
}
|
|
delete pTab;
|
|
pTab = NULL;
|
|
UpdateCtrl();
|
|
return TRUE;
|
|
}
|
|
|
|
BOOL CPropertyListBox::DeleteTab(CString sTabName)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
POSITION pos = FindTab(pTab, sTabName);
|
|
if(pTab == NULL) return FALSE;
|
|
m_listItemTab.RemoveAt(pos);
|
|
|
|
int iIndex = FindString(-1, (LPCTSTR)pTab);
|
|
if(iIndex >= 0)
|
|
{
|
|
CollapseTab(pTab);
|
|
CListBox::DeleteString(iIndex);
|
|
CListBox::SetCurSel(iIndex);
|
|
}
|
|
delete pTab;
|
|
pTab = NULL;
|
|
UpdateCtrl();
|
|
return TRUE;
|
|
}
|
|
|
|
BOOL CPropertyListBox::DeleteTab(CPropertyItemTab*& pTab)
|
|
{
|
|
POSITION pos = m_listItemTab.Find(pTab);
|
|
if(pos == NULL) return FALSE;
|
|
m_listItemTab.RemoveAt(pos);
|
|
|
|
int iIndex = FindString(-1, (LPCTSTR)pTab);
|
|
if(iIndex >= 0)
|
|
{
|
|
CollapseTab(pTab);
|
|
CListBox::DeleteString(iIndex);
|
|
CListBox::SetCurSel(iIndex);
|
|
}
|
|
delete pTab;
|
|
pTab = NULL;
|
|
UpdateCtrl();
|
|
return TRUE;
|
|
}
|
|
|
|
CPropertyItemTab* CPropertyListBox::InsertTab(int iTabIndex, CString sName, BOOL bExpand, BOOL bNameEditable,
|
|
CString sValue, CPropertyItem::ItemStyle nStyle, BOOL bValueEditable)
|
|
{
|
|
CPropertyItemTab* pTab = NULL;
|
|
POSITION pos = NULL;
|
|
if(iTabIndex >= 0) pos = FindTab(pTab, iTabIndex);
|
|
CPropertyItemTab* pNewTab = new CPropertyItemTab(sName, bExpand, sValue, nStyle, bNameEditable, bValueEditable);
|
|
if(pos != NULL) m_listItemTab.InsertBefore(pos, pNewTab);
|
|
else m_listItemTab.AddTail(pNewTab);
|
|
int iIndex = FindString(-1, LPCTSTR(pTab));
|
|
if(iIndex >= 0) CListBox::InsertString(iIndex, LPCTSTR(pNewTab));
|
|
else CListBox::AddString(LPCTSTR(pNewTab));
|
|
UpdateCtrl();
|
|
return pNewTab;
|
|
}
|
|
|
|
CPropertyItemTab* CPropertyListBox::InsertTab(CString sTabName, CString sName, BOOL bExpand, BOOL bNameEditable,
|
|
CString sValue, CPropertyItem::ItemStyle nStyle, BOOL bValueEditable)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
POSITION pos = FindTab(pTab, sTabName);
|
|
CPropertyItemTab* pNewTab = new CPropertyItemTab(sName, bExpand, sValue, nStyle, bNameEditable, bValueEditable);
|
|
if(pos != NULL) m_listItemTab.InsertBefore(pos, pNewTab);
|
|
else m_listItemTab.AddTail(pNewTab);
|
|
int iIndex = FindString(-1, LPCTSTR(pTab));
|
|
if(iIndex >= 0) CListBox::InsertString(iIndex, LPCTSTR(pNewTab));
|
|
else CListBox::AddString(LPCTSTR(pNewTab));
|
|
UpdateCtrl();
|
|
return pNewTab;
|
|
}
|
|
|
|
CPropertyItemTab* CPropertyListBox::InsertTab(CPropertyItemTab*& pTab, CString sName, BOOL bExpand, BOOL bNameEditable,
|
|
CString sValue, CPropertyItem::ItemStyle nStyle, BOOL bValueEditable)
|
|
{
|
|
POSITION pos = m_listItemTab.Find(pTab);
|
|
CPropertyItemTab* pNewTab = new CPropertyItemTab(sName, bExpand, sValue, nStyle, bNameEditable, bValueEditable);
|
|
if(pos != NULL) m_listItemTab.InsertBefore(pos, pNewTab);
|
|
else m_listItemTab.AddTail(pNewTab);
|
|
int iIndex = FindString(-1, LPCTSTR(pTab));
|
|
if(iIndex >= 0) CListBox::InsertString(iIndex, LPCTSTR(pNewTab));
|
|
else CListBox::AddString(LPCTSTR(pNewTab));
|
|
UpdateCtrl();
|
|
return pNewTab;
|
|
}
|
|
|
|
CPropertyItemTab* CPropertyListBox::InsertTab(int iTabIndex, CPropertyItem& item, BOOL bExpand)
|
|
{
|
|
CPropertyItemTab* pTab = NULL;
|
|
POSITION pos = NULL;
|
|
if(iTabIndex >= 0) pos = FindTab(pTab, iTabIndex);
|
|
CPropertyItemTab* pNewTab = new CPropertyItemTab(item, bExpand);
|
|
if(pos != NULL) m_listItemTab.InsertBefore(pos, pNewTab);
|
|
else m_listItemTab.AddTail(pNewTab);
|
|
int iIndex = FindString(-1, LPCTSTR(pTab));
|
|
if(iIndex >= 0) CListBox::InsertString(iIndex, LPCTSTR(pNewTab));
|
|
else CListBox::AddString(LPCTSTR(pNewTab));
|
|
UpdateCtrl();
|
|
return pNewTab;
|
|
}
|
|
|
|
CPropertyItemTab* CPropertyListBox::InsertTab(CString sTabName, CPropertyItem& item, BOOL bExpand)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
POSITION pos = FindTab(pTab, sTabName);
|
|
CPropertyItemTab* pNewTab = new CPropertyItemTab(item, bExpand);
|
|
if(pos != NULL) m_listItemTab.InsertBefore(pos, pNewTab);
|
|
else m_listItemTab.AddTail(pNewTab);
|
|
int iIndex = FindString(-1, LPCTSTR(pTab));
|
|
if(iIndex >= 0) CListBox::InsertString(iIndex, LPCTSTR(pNewTab));
|
|
else CListBox::AddString(LPCTSTR(pNewTab));
|
|
UpdateCtrl();
|
|
return pNewTab;
|
|
}
|
|
|
|
CPropertyItemTab* CPropertyListBox::InsertTab(CPropertyItemTab*& pTab, CPropertyItem& item, BOOL bExpand)
|
|
{
|
|
POSITION pos = m_listItemTab.Find(pTab);
|
|
CPropertyItemTab* pNewTab = new CPropertyItemTab(item, bExpand);
|
|
if(pos != NULL) m_listItemTab.InsertBefore(pos, pNewTab);
|
|
else m_listItemTab.AddTail(pNewTab);
|
|
int iIndex = FindString(-1, LPCTSTR(pTab));
|
|
if(iIndex >= 0) CListBox::InsertString(iIndex, LPCTSTR(pNewTab));
|
|
else CListBox::AddString(LPCTSTR(pNewTab));
|
|
UpdateCtrl();
|
|
return pNewTab;
|
|
}
|
|
|
|
CPropertyItemTab* CPropertyListBox::InsertTab(int iTabIndex, CPropertyItemTab& tab)
|
|
{
|
|
CPropertyItemTab* pTab = NULL;
|
|
POSITION pos = NULL;
|
|
if(iTabIndex >= 0) pos = FindTab(pTab, iTabIndex);
|
|
CPropertyItemTab* pNewTab = new CPropertyItemTab();
|
|
*pNewTab = tab;
|
|
if(pos != NULL) m_listItemTab.InsertBefore(pos, pNewTab);
|
|
else m_listItemTab.AddTail(pNewTab);
|
|
int iIndex = FindString(-1, LPCTSTR(pTab));
|
|
if(iIndex >= 0) CListBox::InsertString(iIndex, LPCTSTR(pNewTab));
|
|
else CListBox::AddString(LPCTSTR(pNewTab));
|
|
if(pNewTab->m_bExpand)
|
|
{
|
|
pNewTab->m_bExpand = FALSE;
|
|
ExpandTab(pNewTab);
|
|
}
|
|
UpdateCtrl();
|
|
return pNewTab;
|
|
}
|
|
|
|
CPropertyItemTab* CPropertyListBox::InsertTab(CString sTabName, CPropertyItemTab& tab)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
POSITION pos = FindTab(pTab, sTabName);
|
|
CPropertyItemTab* pNewTab = new CPropertyItemTab();
|
|
*pNewTab = tab;
|
|
if(pos != NULL) m_listItemTab.InsertBefore(pos, pNewTab);
|
|
else m_listItemTab.AddTail(pNewTab);
|
|
int iIndex = FindString(-1, LPCTSTR(pTab));
|
|
if(iIndex >= 0) CListBox::InsertString(iIndex, LPCTSTR(pNewTab));
|
|
else CListBox::AddString(LPCTSTR(pNewTab));
|
|
if(pNewTab->m_bExpand)
|
|
{
|
|
pNewTab->m_bExpand = FALSE;
|
|
ExpandTab(pNewTab);
|
|
}
|
|
UpdateCtrl();
|
|
return pNewTab;
|
|
}
|
|
|
|
CPropertyItemTab* CPropertyListBox::InsertTab(CPropertyItemTab*& pTab, CPropertyItemTab& tab)
|
|
{
|
|
POSITION pos = m_listItemTab.Find(pTab);
|
|
CPropertyItemTab* pNewTab = new CPropertyItemTab();
|
|
*pNewTab = tab;
|
|
if(pos != NULL) m_listItemTab.InsertBefore(pos, pNewTab);
|
|
else m_listItemTab.AddTail(pNewTab);
|
|
int iIndex = FindString(-1, LPCTSTR(pTab));
|
|
if(iIndex >= 0) CListBox::InsertString(iIndex, LPCTSTR(pNewTab));
|
|
else CListBox::AddString(LPCTSTR(pNewTab));
|
|
if(pNewTab->m_bExpand)
|
|
{
|
|
pNewTab->m_bExpand = FALSE;
|
|
ExpandTab(pNewTab);
|
|
}
|
|
UpdateCtrl();
|
|
return pNewTab;
|
|
}
|
|
|
|
BOOL CPropertyListBox::AddItem(CString sTabName, CString sName, CString sValue,
|
|
CPropertyItem::ItemStyle nStyle, BOOL bValueEditable, BOOL bNameEditable, CStringList* pStrList, CString sFileFilter)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
FindTab(pTab, sTabName);
|
|
if(pTab == NULL) return FALSE;
|
|
return AddItem(pTab, sName, sValue, nStyle, bValueEditable, bNameEditable, pStrList, sFileFilter);
|
|
}
|
|
|
|
BOOL CPropertyListBox::AddItem(UINT nTabIndex, CString sName, CString sValue,
|
|
CPropertyItem::ItemStyle nStyle, BOOL bValueEditable, BOOL bNameEditable, CStringList* pStrList, CString sFileFilter)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
FindTab(pTab, nTabIndex);
|
|
if(pTab == NULL) return FALSE;
|
|
return AddItem(pTab, sName, sValue, nStyle, bValueEditable, bNameEditable, pStrList, sFileFilter);
|
|
}
|
|
|
|
BOOL CPropertyListBox::AddItem(CPropertyItemTab*& pTab, CString sName, CString sValue,
|
|
CPropertyItem::ItemStyle nStyle, BOOL bValueEditable, BOOL bNameEditable, CStringList* pStrList, CString sFileFilter)
|
|
{
|
|
int iIndex = FindString(-1, (LPCTSTR)pTab);
|
|
if(iIndex < 0) return FALSE;
|
|
|
|
CPropertyItem* pItem = new CPropertyItem(sName, sValue, nStyle, bNameEditable, bValueEditable, pStrList, sFileFilter);
|
|
pTab->m_listItem.AddTail(pItem);
|
|
if(pTab->m_bExpand)
|
|
{
|
|
iIndex += pTab->m_listItem.GetCount();
|
|
CListBox::InsertString(iIndex, LPCTSTR(pItem));
|
|
}
|
|
UpdateCtrl();
|
|
return TRUE;
|
|
}
|
|
|
|
BOOL CPropertyListBox::AddItem(UINT nTabIndex, CPropertyItem& item)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
FindTab(pTab, nTabIndex);
|
|
if(pTab == NULL) return FALSE;
|
|
return AddItem(pTab, item);
|
|
}
|
|
|
|
BOOL CPropertyListBox::AddItem(CString sTabName, CPropertyItem& item)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
FindTab(pTab, sTabName);
|
|
if(pTab == NULL) return FALSE;
|
|
return AddItem(pTab, item);
|
|
}
|
|
|
|
BOOL CPropertyListBox::AddItem(CPropertyItemTab*& pTab, CPropertyItem& item)
|
|
{
|
|
int iIndex = FindString(-1, (LPCTSTR)pTab);
|
|
if(iIndex < 0) return FALSE;
|
|
|
|
CPropertyItem* pItem = new CPropertyItem();
|
|
*pItem = item;
|
|
pTab->m_listItem.AddTail(pItem);
|
|
if(pTab->m_bExpand)
|
|
{
|
|
iIndex += pTab->m_listItem.GetCount();
|
|
CListBox::InsertString(iIndex, LPCTSTR(pItem));
|
|
}
|
|
UpdateCtrl();
|
|
return TRUE;
|
|
}
|
|
|
|
BOOL CPropertyListBox::DeleteItem(UINT nTabIndex, UINT nItemIndex)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
FindTab(pTab, nTabIndex);
|
|
if(pTab == NULL) return FALSE;
|
|
return DeleteItem(pTab, nItemIndex);
|
|
}
|
|
|
|
BOOL CPropertyListBox::DeleteItem(UINT nTabIndex, CString sItemName)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
FindTab(pTab, nTabIndex);
|
|
if(pTab == NULL) return FALSE;
|
|
return DeleteItem(pTab, sItemName);
|
|
}
|
|
|
|
BOOL CPropertyListBox::DeleteItem(UINT nTabIndex, CPropertyItem*& pItem)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
FindTab(pTab, nTabIndex);
|
|
if(pTab == NULL) return FALSE;
|
|
return DeleteItem(pTab, pItem);
|
|
}
|
|
|
|
BOOL CPropertyListBox::DeleteItem(CString sTabName, UINT nItemIndex)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
FindTab(pTab, sTabName);
|
|
if(pTab == NULL) return FALSE;
|
|
return DeleteItem(pTab, nItemIndex);
|
|
}
|
|
|
|
BOOL CPropertyListBox::DeleteItem(CString sTabName, CString sItemName)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
FindTab(pTab, sTabName);
|
|
if(pTab == NULL) return FALSE;
|
|
return DeleteItem(pTab, sItemName);
|
|
}
|
|
|
|
BOOL CPropertyListBox::DeleteItem(CString sTabName, CPropertyItem*& pItem)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
FindTab(pTab, sTabName);
|
|
if(pTab == NULL) return FALSE;
|
|
return DeleteItem(pTab, pItem);
|
|
}
|
|
|
|
BOOL CPropertyListBox::DeleteItem(CPropertyItemTab*& pTab, UINT nItemIndex)
|
|
{
|
|
CPropertyItem* pItem;
|
|
POSITION pos = FindItem(pItem, pTab, nItemIndex);
|
|
if(pItem == NULL) return FALSE;
|
|
pTab->m_listItem.RemoveAt(pos);
|
|
|
|
if(pTab->m_bExpand)
|
|
{
|
|
int iIndex = FindString(-1, (LPCTSTR)pItem);
|
|
if(iIndex >= 0) CListBox::DeleteString(iIndex);
|
|
CListBox::SetCurSel(iIndex);
|
|
}
|
|
delete pItem;
|
|
pItem = NULL;
|
|
UpdateCtrl();
|
|
return TRUE;
|
|
}
|
|
|
|
BOOL CPropertyListBox::DeleteItem(CPropertyItemTab*& pTab, CString sItemName)
|
|
{
|
|
CPropertyItem* pItem;
|
|
POSITION pos = FindItem(pItem, pTab, sItemName);
|
|
if(pItem == NULL) return FALSE;
|
|
pTab->m_listItem.RemoveAt(pos);
|
|
|
|
if(pTab->m_bExpand)
|
|
{
|
|
int iIndex = FindString(-1, (LPCTSTR)pItem);
|
|
if(iIndex >= 0) CListBox::DeleteString(iIndex);
|
|
CListBox::SetCurSel(iIndex);
|
|
}
|
|
delete pItem;
|
|
pItem = NULL;
|
|
UpdateCtrl();
|
|
return TRUE;
|
|
}
|
|
|
|
BOOL CPropertyListBox::DeleteItem(CPropertyItemTab*& pTab, CPropertyItem*& pItem)
|
|
{
|
|
POSITION pos = pTab->m_listItem.Find(pItem);
|
|
if(pos == NULL) return FALSE;
|
|
pTab->m_listItem.RemoveAt(pos);
|
|
|
|
if(pTab->m_bExpand)
|
|
{
|
|
int iIndex = FindString(-1, (LPCTSTR)pItem);
|
|
if(iIndex >= 0) CListBox::DeleteString(iIndex);
|
|
CListBox::SetCurSel(iIndex);
|
|
}
|
|
delete pItem;
|
|
pItem = NULL;
|
|
UpdateCtrl();
|
|
return TRUE;
|
|
}
|
|
|
|
BOOL CPropertyListBox::InsertItem(UINT nTabIndex, int iItemIndex, CPropertyItem& item)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
FindTab(pTab, nTabIndex);
|
|
if(pTab == NULL) return FALSE;
|
|
return InsertItem(pTab, iItemIndex, item);
|
|
}
|
|
|
|
BOOL CPropertyListBox::InsertItem(CPropertyItemTab*& pTab, int iItemIndex, CPropertyItem& item)
|
|
{
|
|
CPropertyItem* pNewItem = new CPropertyItem();
|
|
*pNewItem = item;
|
|
POSITION pos = NULL;
|
|
CPropertyItem* pItem;
|
|
if(iItemIndex >= 0) pos = FindItem(pItem, pTab, iItemIndex);
|
|
if(pos != NULL) pTab->m_listItem.InsertBefore(pos, pNewItem);
|
|
else pTab->m_listItem.AddHead(pNewItem);
|
|
|
|
if(pTab->m_bExpand)
|
|
{
|
|
int iIndex = FindString(-1, (LPCTSTR)pItem);
|
|
if(iIndex < 0)
|
|
{
|
|
iIndex = FindString(-1, (LPCTSTR)pTab);
|
|
if(iIndex >= 0) iIndex++;
|
|
}
|
|
if(iIndex >= 0) CListBox::InsertString(iIndex, (LPCTSTR)pNewItem);
|
|
}
|
|
UpdateCtrl();
|
|
return TRUE;
|
|
}
|
|
|
|
BOOL CPropertyListBox::InsertItem(UINT nTabIndex, CPropertyItem*& pItem, CPropertyItem& item)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
FindTab(pTab, nTabIndex);
|
|
if(pTab == NULL) return FALSE;
|
|
return InsertItem(pTab, pItem, item);
|
|
}
|
|
|
|
BOOL CPropertyListBox::InsertItem(CPropertyItemTab*& pTab, CPropertyItem*& pItem, CPropertyItem& item)
|
|
{
|
|
CPropertyItem* pNewItem = new CPropertyItem();
|
|
*pNewItem = item;
|
|
POSITION pos = pTab->m_listItem.Find(pItem);
|
|
if(pos != NULL) pTab->m_listItem.InsertBefore(pos, pNewItem);
|
|
else pTab->m_listItem.AddHead(pNewItem);
|
|
|
|
if(pTab->m_bExpand)
|
|
{
|
|
int iIndex = FindString(-1, (LPCTSTR)pItem);
|
|
if(iIndex < 0)
|
|
{
|
|
iIndex = FindString(-1, (LPCTSTR)pTab);
|
|
if(iIndex >= 0) iIndex++;
|
|
}
|
|
if(iIndex >= 0) CListBox::InsertString(iIndex, (LPCTSTR)pNewItem);
|
|
}
|
|
UpdateCtrl();
|
|
return TRUE;
|
|
}
|
|
|
|
POSITION CPropertyListBox::GetFirstTabPositon()
|
|
{
|
|
return m_listItemTab.GetHeadPosition();
|
|
}
|
|
|
|
POSITION CPropertyListBox::GetLastTabPositon()
|
|
{
|
|
return m_listItemTab.GetTailPosition();
|
|
}
|
|
|
|
CPropertyItemTab* CPropertyListBox::GetNextTab(POSITION& pos)
|
|
{
|
|
return m_listItemTab.GetNext(pos);
|
|
}
|
|
|
|
CPropertyItemTab* CPropertyListBox::GetPrevTab(POSITION& pos)
|
|
{
|
|
return m_listItemTab.GetPrev(pos);
|
|
}
|
|
|
|
POSITION CPropertyListBox::GetTabPosition(CPropertyItemTab* pTab)
|
|
{
|
|
return m_listItemTab.Find(pTab);
|
|
}
|
|
|
|
POSITION CPropertyListBox::FindTab(CPropertyItemTab*& pTab, CString sTabName)
|
|
{
|
|
pTab = NULL;
|
|
CPropertyItemTab* pTabTemp;
|
|
POSITION pos = m_listItemTab.GetHeadPosition();
|
|
POSITION posBak = NULL;
|
|
while(pos != NULL)
|
|
{
|
|
posBak = pos;
|
|
pTabTemp = (CPropertyItemTab*)m_listItemTab.GetNext(pos);
|
|
if(pTabTemp->m_sName == sTabName)
|
|
{
|
|
pTab = pTabTemp;
|
|
return posBak;
|
|
}
|
|
}
|
|
return NULL;
|
|
}
|
|
|
|
POSITION CPropertyListBox::FindTab(CPropertyItemTab*& pTab, UINT nTabIndex)
|
|
{
|
|
pTab = NULL;
|
|
POSITION pos = m_listItemTab.FindIndex(nTabIndex);
|
|
if(pos != NULL) pTab = (CPropertyItemTab*)m_listItemTab.GetAt(pos);
|
|
return pos;
|
|
}
|
|
|
|
POSITION CPropertyListBox::FindItem(CPropertyItem*& pItem, CPropertyItemTab*& pTab, UINT nItemIndex)
|
|
{
|
|
pItem = NULL;
|
|
POSITION pos = pTab->m_listItem.FindIndex(nItemIndex);
|
|
if(pos != NULL) pItem = (CPropertyItem*)pTab->m_listItem.GetAt(pos);
|
|
return pos;
|
|
}
|
|
|
|
POSITION CPropertyListBox::FindItem(CPropertyItem*& pItem, CPropertyItemTab*& pTab, CString sItemName)
|
|
{
|
|
pItem = NULL;
|
|
CPropertyItem* pItemTemp;
|
|
POSITION pos = pTab->m_listItem.GetHeadPosition();
|
|
POSITION posBak = NULL;
|
|
while(pos != NULL)
|
|
{
|
|
posBak = pos;
|
|
pItemTemp = (CPropertyItem*)pTab->m_listItem.GetNext(pos);
|
|
if(pItemTemp->m_sName == sItemName)
|
|
{
|
|
pItem = pItemTemp;
|
|
return posBak;
|
|
}
|
|
}
|
|
return NULL;
|
|
}
|
|
|
|
int CPropertyListBox::FindTabIndex(CString sTabName, UINT nStart/* = 0*/)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
POSITION pos = m_listItemTab.FindIndex(nStart);
|
|
while(pos != NULL)
|
|
{
|
|
pTab = (CPropertyItemTab*)m_listItemTab.GetNext(pos);
|
|
if(pTab->m_sName == sTabName) return nStart;
|
|
nStart++;
|
|
}
|
|
return -1;
|
|
}
|
|
|
|
int CPropertyListBox::FindTabIndex(CPropertyItemTab* pTab, UINT nStart)
|
|
{
|
|
CPropertyItemTab* pTab1;
|
|
POSITION pos = m_listItemTab.FindIndex(nStart);
|
|
while(pos != NULL)
|
|
{
|
|
pTab1 = (CPropertyItemTab*)m_listItemTab.GetNext(pos);
|
|
if(pTab == pTab1) return nStart;
|
|
nStart++;
|
|
}
|
|
return -1;
|
|
}
|
|
|
|
int CPropertyListBox::FindItemIndex(CString sItemName, UINT nTabIndex, UINT nStart/* = 0*/)
|
|
{
|
|
POSITION pos = m_listItemTab.FindIndex(nTabIndex);
|
|
if(pos == NULL) return -1;
|
|
CPropertyItemTab* pTab = (CPropertyItemTab*)m_listItemTab.GetAt(pos);
|
|
|
|
CPropertyItem* pItem;
|
|
pos = pTab->m_listItem.FindIndex(nStart);
|
|
while(pos != NULL)
|
|
{
|
|
pItem = (CPropertyItem*)pTab->m_listItem.GetNext(pos);
|
|
if(pItem->m_sName == sItemName) return nStart;
|
|
nStart++;
|
|
}
|
|
return -1;
|
|
}
|
|
|
|
int CPropertyListBox::FindIndex(CPropertyItem* pItem)
|
|
{
|
|
return CListBox::FindString(-1, (LPCTSTR)pItem);
|
|
}
|
|
|
|
int CPropertyListBox::GetCurSel()
|
|
{
|
|
return CListBox::GetCurSel();
|
|
}
|
|
|
|
void CPropertyListBox::GetCurSel(int& iTabIndex, int& iItemIndex)
|
|
{
|
|
iTabIndex = -1;
|
|
iItemIndex = -1;
|
|
int iCurSel = CListBox::GetCurSel();
|
|
if(iCurSel < 0) return;
|
|
CPropertyItem* pItem = (CPropertyItem*)GetItemData(iCurSel);
|
|
if(pItem->IsKindOf(RUNTIME_CLASS(CPropertyItemTab)))
|
|
{
|
|
CPropertyItemTab* pTab = (CPropertyItemTab*)pItem;
|
|
POSITION pos = m_listItemTab.GetHeadPosition();
|
|
while(pos != NULL)
|
|
{
|
|
iTabIndex++;
|
|
if(pTab == (CPropertyItemTab*)m_listItemTab.GetNext(pos)) break;
|
|
}
|
|
return;
|
|
}
|
|
|
|
int iIndex = -1;
|
|
CPropertyItemTab* pTab;
|
|
POSITION pos = m_listItemTab.GetHeadPosition();
|
|
while(pos != NULL)
|
|
{
|
|
iTabIndex++;
|
|
iIndex++;
|
|
pTab = (CPropertyItemTab*)m_listItemTab.GetNext(pos);
|
|
if(pTab->m_bExpand) iIndex += pTab->m_listItem.GetCount();
|
|
if(iCurSel <= iIndex)
|
|
{
|
|
iIndex = FindString(-1, LPCTSTR(pTab));
|
|
if(iIndex >= 0) iItemIndex = iCurSel - iIndex - 1;
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
void CPropertyListBox::GetCurSel(int& iTabIndex, CPropertyItem*& pItem)
|
|
{
|
|
iTabIndex = -1;
|
|
pItem = NULL;
|
|
int iCurSel = CListBox::GetCurSel();
|
|
if(iCurSel < 0) return;
|
|
pItem = (CPropertyItem*)GetItemData(iCurSel);
|
|
if(pItem->IsKindOf(RUNTIME_CLASS(CPropertyItemTab)))
|
|
{
|
|
CPropertyItemTab* pTab = (CPropertyItemTab*)pItem;
|
|
pItem = NULL;
|
|
POSITION pos = m_listItemTab.GetHeadPosition();
|
|
while(pos != NULL)
|
|
{
|
|
iTabIndex++;
|
|
if(pTab == (CPropertyItemTab*)m_listItemTab.GetNext(pos)) break;
|
|
}
|
|
return;
|
|
}
|
|
|
|
int iIndex = -1;
|
|
CPropertyItemTab* pTab;
|
|
POSITION pos = m_listItemTab.GetHeadPosition();
|
|
while(pos != NULL)
|
|
{
|
|
iTabIndex++;
|
|
iIndex++;
|
|
pTab = (CPropertyItemTab*)m_listItemTab.GetNext(pos);
|
|
if(pTab->m_bExpand) iIndex += pTab->m_listItem.GetCount();
|
|
if(iCurSel <= iIndex) break;
|
|
}
|
|
}
|
|
void CPropertyListBox::GetCurSel(CPropertyItemTab*& pTab, int& iItemIndex)
|
|
{
|
|
pTab = NULL;
|
|
iItemIndex = -1;
|
|
int iCurSel = CListBox::GetCurSel();
|
|
if(iCurSel < 0) return;
|
|
CPropertyItem* pItem = (CPropertyItem*)GetItemData(iCurSel);
|
|
if(pItem->IsKindOf(RUNTIME_CLASS(CPropertyItemTab)))
|
|
{
|
|
pTab = (CPropertyItemTab*)pItem;
|
|
return;
|
|
}
|
|
|
|
int iIndex = -1;
|
|
CPropertyItemTab* pTabTemp;
|
|
POSITION pos = m_listItemTab.GetHeadPosition();
|
|
while(pos != NULL)
|
|
{
|
|
iIndex++;
|
|
pTabTemp = (CPropertyItemTab*)m_listItemTab.GetNext(pos);
|
|
if(pTabTemp->m_bExpand) iIndex += pTabTemp->m_listItem.GetCount();
|
|
if(iCurSel <= iIndex)
|
|
{
|
|
pTab = pTabTemp;
|
|
iIndex = FindString(-1, LPCTSTR(pTab));
|
|
if(iIndex >= 0) iItemIndex = iCurSel - iIndex - 1;
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
void CPropertyListBox::GetCurSel(CPropertyItemTab*& pTab, CPropertyItem*& pItem)
|
|
{
|
|
pTab = NULL;
|
|
pItem = NULL;
|
|
int iCurSel = CListBox::GetCurSel();
|
|
if(iCurSel < 0) return;
|
|
pItem = (CPropertyItem*)GetItemData(iCurSel);
|
|
if(pItem->IsKindOf(RUNTIME_CLASS(CPropertyItemTab)))
|
|
{
|
|
pTab = (CPropertyItemTab*)pItem;
|
|
pItem = NULL;
|
|
return;
|
|
}
|
|
int iIndex = -1;
|
|
CPropertyItemTab* pTabTemp;
|
|
POSITION pos = m_listItemTab.GetHeadPosition();
|
|
while(pos != NULL)
|
|
{
|
|
iIndex++;
|
|
pTabTemp = (CPropertyItemTab*)m_listItemTab.GetNext(pos);
|
|
if(pTabTemp->m_bExpand) iIndex += pTabTemp->m_listItem.GetCount();
|
|
if(iCurSel <= iIndex) {pTab = pTabTemp; break;}
|
|
}
|
|
}
|
|
|
|
void CPropertyListBox::SetCurSel(int iTabIndex, int iItemIndex)
|
|
{
|
|
if(iTabIndex < 0)
|
|
{
|
|
CListBox::SetCurSel(-1);
|
|
return;
|
|
}
|
|
CPropertyItemTab* pTab;
|
|
if(FindTab(pTab, iTabIndex) == NULL) return;
|
|
if(!pTab->m_bExpand || iItemIndex < 0)
|
|
{
|
|
CListBox::SetCurSel(FindString(-1, (LPCTSTR)pTab));
|
|
UpdateCtrl();
|
|
return;
|
|
}
|
|
CPropertyItem* pItem;
|
|
if(FindItem(pItem, pTab, iItemIndex) == NULL) return;
|
|
CListBox::SetCurSel(FindString(-1, (LPCTSTR)pItem));
|
|
UpdateCtrl();
|
|
}
|
|
|
|
void CPropertyListBox::SetCurSel(int iTabIndex, CPropertyItem*& pItem)
|
|
{
|
|
if(iTabIndex < 0)
|
|
{
|
|
CListBox::SetCurSel(-1);
|
|
return;
|
|
}
|
|
CPropertyItemTab* pTab;
|
|
if(FindTab(pTab, iTabIndex) == NULL) return;
|
|
if(!pTab->m_bExpand || pItem == NULL)
|
|
{
|
|
CListBox::SetCurSel(FindString(-1, (LPCTSTR)pTab));
|
|
UpdateCtrl();
|
|
return;
|
|
}
|
|
CListBox::SetCurSel(FindString(-1, (LPCTSTR)pItem));
|
|
UpdateCtrl();
|
|
}
|
|
|
|
void CPropertyListBox::SetCurSel(CPropertyItemTab*& pTab, int iItemIndex)
|
|
{
|
|
if(pTab == NULL)
|
|
{
|
|
CListBox::SetCurSel(-1);
|
|
return;
|
|
}
|
|
if(!pTab->m_bExpand || iItemIndex < 0)
|
|
{
|
|
CListBox::SetCurSel(FindString(-1, (LPCTSTR)pTab));
|
|
UpdateCtrl();
|
|
return;
|
|
}
|
|
CPropertyItem* pItem;
|
|
if(FindItem(pItem, pTab, iItemIndex) == NULL) return;
|
|
CListBox::SetCurSel(FindString(-1, (LPCTSTR)pItem));
|
|
UpdateCtrl();
|
|
}
|
|
|
|
void CPropertyListBox::SetCurSel(CPropertyItemTab*& pTab, CPropertyItem*& pItem)
|
|
{
|
|
if(pTab == NULL)
|
|
{
|
|
CListBox::SetCurSel(-1);
|
|
return;
|
|
}
|
|
if(!pTab->m_bExpand || pItem == NULL)
|
|
{
|
|
CListBox::SetCurSel(FindString(-1, (LPCTSTR)pTab));
|
|
UpdateCtrl();
|
|
return;
|
|
}
|
|
CListBox::SetCurSel(FindString(-1, (LPCTSTR)pItem));
|
|
UpdateCtrl();
|
|
}
|
|
|
|
void CPropertyListBox::CollapseTab(CString sTabName)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
FindTab(pTab, sTabName);
|
|
if(pTab != NULL) CollapseTab(pTab);
|
|
}
|
|
|
|
void CPropertyListBox::CollapseTab(UINT nTabIndex)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
FindTab(pTab, nTabIndex);
|
|
if(pTab != NULL) CollapseTab(pTab);
|
|
}
|
|
|
|
void CPropertyListBox::CollapseTab(CPropertyItemTab *&pTab)
|
|
{
|
|
int iIndex = FindString(-1, (LPCTSTR)pTab);
|
|
if(!pTab->m_bExpand || iIndex < 0) return;
|
|
pTab->m_bExpand = FALSE;
|
|
for(int i = iIndex + pTab->m_listItem.GetCount(); i > iIndex; i--) CListBox::DeleteString(i);
|
|
}
|
|
|
|
void CPropertyListBox::ExpandTab(CString sTabName)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
FindTab(pTab, sTabName);
|
|
if(pTab != NULL) ExpandTab(pTab);
|
|
}
|
|
|
|
void CPropertyListBox::ExpandTab(UINT nTabIndex)
|
|
{
|
|
CPropertyItemTab* pTab;
|
|
FindTab(pTab, nTabIndex);
|
|
if(pTab != NULL) ExpandTab(pTab);
|
|
}
|
|
|
|
void CPropertyListBox::ExpandTab(CPropertyItemTab *&pTab)
|
|
{
|
|
int iIndex = FindString(-1, (LPCTSTR)pTab);
|
|
if(pTab->m_bExpand || iIndex < 0) return;
|
|
int iBackIndex = iIndex;
|
|
|
|
pTab->m_bExpand = TRUE;
|
|
CPropertyItem* pItem;
|
|
POSITION pos = pTab->m_listItem.GetHeadPosition();
|
|
while(pos != NULL)
|
|
{
|
|
iIndex++;
|
|
pItem = (CPropertyItem*)pTab->m_listItem.GetNext(pos);
|
|
CListBox::InsertString(iIndex, LPCTSTR(pItem));
|
|
}
|
|
|
|
// 展开后设置可见
|
|
CRect rcClient;
|
|
CListBox::GetClientRect(rcClient);
|
|
int iCount = rcClient.Height() / CListBox::GetItemHeight(iIndex);
|
|
int iTop = CListBox::GetTopIndex();
|
|
int iScroll = (iBackIndex + pTab->m_listItem.GetCount()) - (iTop + iCount);
|
|
if (iScroll > 0)
|
|
{
|
|
iTop += (iScroll + 1);
|
|
if (iTop > iBackIndex) iTop = iBackIndex;
|
|
CListBox::SetTopIndex(iTop);
|
|
}
|
|
}
|
|
|
|
void CPropertyListBox::DoCollapseExpand(CPropertyItem*& pItem)
|
|
{
|
|
if(pItem->IsKindOf(RUNTIME_CLASS(CPropertyItemTab)))
|
|
{
|
|
CPropertyItemTab* pTab = (CPropertyItemTab*)pItem;
|
|
if(pTab->m_bExpand) CollapseTab(pTab);
|
|
else ExpandTab(pTab);
|
|
}
|
|
}
|
|
|
|
///////////////////////////////////////////////////////////////////////////
|
|
// Avoid the origin function
|
|
|
|
int CPropertyListBox::AddString(LPCTSTR lpszItem)
|
|
{
|
|
return -1;
|
|
}
|
|
|
|
int CPropertyListBox::InsertString(int nIndex, LPCTSTR lpszItem)
|
|
{
|
|
return -1;
|
|
}
|
|
|
|
int CPropertyListBox::DeleteString(UINT nIndex)
|
|
{
|
|
return -1;
|
|
}
|
|
|
|
int CPropertyListBox::SetItemData(int nIndex, DWORD dwItemData)
|
|
{
|
|
return -1;
|
|
}
|
|
|
|
void CPropertyListBox::OnMouseMove(UINT nFlags, CPoint point)
|
|
{
|
|
if (m_bSeperate)
|
|
{
|
|
DrawSeperator();
|
|
int iOffset = point.x - m_rcTrack.CenterPoint().x;
|
|
m_rcTrack.OffsetRect(iOffset, 0);
|
|
DrawSeperator();
|
|
|
|
return;
|
|
}
|
|
|
|
CListBox::OnMouseMove(nFlags, point);
|
|
|
|
BOOL bOutSide;
|
|
int iItem = CListBox::ItemFromPoint(point, bOutSide);
|
|
if(bOutSide || iItem < 0) return;
|
|
|
|
CRect rect, rcValue;
|
|
CListBox::GetItemRect(iItem, rect);
|
|
rect.left += m_nLeftBorder;
|
|
rect.OffsetRect(2, 1);
|
|
rcValue = GetItemValueRect(rect);
|
|
|
|
CPropertyItem* pItem = (CPropertyItem*)CListBox::GetItemData(iItem);
|
|
if(rect.PtInRect(point))
|
|
{
|
|
m_titletip.Show(rect, pItem->m_sName, 0);
|
|
}
|
|
else if(rcValue.PtInRect(point))
|
|
{
|
|
m_titletip.Show(rcValue, pItem->m_sValue, 0);
|
|
}
|
|
}
|
|
|
|
void CPropertyListBox::PreSubclassWindow()
|
|
{
|
|
m_titletip.Create(this);
|
|
CListBox::PreSubclassWindow();
|
|
}
|
|
|
|
LRESULT CPropertyListBox::OnChildKillFoucs(WPARAM wParam, LPARAM lParam)
|
|
{
|
|
UNUSED_ALWAYS( wParam );
|
|
LPIPCENDINFO lpEndInfo = (LPIPCENDINFO)lParam;
|
|
if( lpEndInfo->uKind == IPEK_KILLFOUCE )
|
|
{
|
|
if( m_pWndCtrl != NULL && m_pWndCtrl->IsWindowVisible()
|
|
&& lpEndInfo->hNewWnd != m_pWndCtrl-> m_hWnd )
|
|
{
|
|
if( m_bEditName && m_pWndCtrl->IsKindOf(RUNTIME_CLASS(CInPlaceEdit)) )
|
|
{
|
|
GetParent()->SendMessage(WM_USER_CHILDVALUECHANGED, MAKEWPARAM(3, MAKEWORD(1, m_bEditName)), (LPARAM)m_hWnd);
|
|
}
|
|
}
|
|
}
|
|
|
|
return 0l;
|
|
}
|
|
|
|
void CPropertyListBox::OnVScroll(UINT nSBCode, UINT nPos, CScrollBar* pScrollBar)
|
|
{
|
|
if(pScrollBar && pScrollBar->m_hWnd == m_pWndSpin->m_hWnd) return;
|
|
|
|
CListBox::OnVScroll(nSBCode, nPos, pScrollBar);
|
|
}
|
|
|
|
BOOL CPropertyListBox::OnSetCursor(CWnd* pWnd, UINT nHitTest, UINT message)
|
|
{
|
|
if (IsHitOnSeperator())
|
|
{
|
|
SetCursor(AfxGetApp()->LoadStandardCursor(IDC_SIZEWE));
|
|
return TRUE;
|
|
}
|
|
|
|
return CListBox::OnSetCursor(pWnd, nHitTest, message);
|
|
}
|
|
|
|
BOOL CPropertyListBox::IsHitOnSeperator(CRect* pRect/* = NULL*/)
|
|
{
|
|
CPoint pt;
|
|
GetCursorPos(&pt);
|
|
CListBox::ScreenToClient(&pt);
|
|
|
|
CRect rc;
|
|
CListBox::GetItemRect(0, rc);
|
|
rc.left += m_nLeftBorder + m_nNameWidth - 1;
|
|
rc.right = rc.left + 3;
|
|
rc.bottom = rc.top + rc.Height() * CListBox::GetCount();
|
|
|
|
if (pRect) pRect->SetRect(rc.left, rc.top, rc.right, rc.bottom);
|
|
return rc.PtInRect(pt);
|
|
}
|
|
|
|
void CPropertyListBox::OnLButtonUp(UINT nFlags, CPoint point)
|
|
{
|
|
if (m_bSeperate)
|
|
{
|
|
StopTracking();
|
|
return;
|
|
}
|
|
|
|
CListBox::OnLButtonUp(nFlags, point);
|
|
}
|
|
|
|
void CPropertyListBox::OnCaptureChanged(CWnd *pWnd)
|
|
{
|
|
if (m_bSeperate) StopTracking(TRUE);
|
|
|
|
CListBox::OnCaptureChanged(pWnd);
|
|
}
|
|
|
|
void CPropertyListBox::StartTracking()
|
|
{
|
|
SetCapture();
|
|
RedrawWindow(NULL, NULL, RDW_ALLCHILDREN | RDW_UPDATENOW);
|
|
LockWindowUpdate();
|
|
m_bSeperate = TRUE;
|
|
m_rcTrack = m_rcSeperator;
|
|
|
|
DrawSeperator();
|
|
}
|
|
|
|
void CPropertyListBox::StopTracking(BOOL bCancel/* = FALSE*/)
|
|
{
|
|
DrawSeperator();
|
|
UnlockWindowUpdate();
|
|
ReleaseCapture();
|
|
m_bSeperate = FALSE;
|
|
|
|
if (bCancel) return;
|
|
|
|
int iOffset = m_rcTrack.left - m_rcSeperator.left;
|
|
if (iOffset == 0)
|
|
{
|
|
DrawSeperator();
|
|
return;
|
|
}
|
|
|
|
CRect rc;
|
|
CListBox::GetItemRect(0, rc);
|
|
UINT nMaxWidth = rc.Width() - m_nLeftBorder - 2;
|
|
|
|
m_nNameWidth += iOffset;
|
|
if (int(m_nNameWidth) < 1) m_nNameWidth = 1;
|
|
else if (m_nNameWidth > nMaxWidth) m_nNameWidth = nMaxWidth;
|
|
|
|
UpdateCtrl();
|
|
CListBox::Invalidate();
|
|
}
|
|
|
|
void CPropertyListBox::DrawSeperator()
|
|
{
|
|
CRect rc;
|
|
CListBox::GetClientRect(&rc);
|
|
rc.OffsetRect(0, 2);
|
|
CRgn rg;
|
|
rg.CreateRectRgnIndirect(&rc);
|
|
|
|
CDC *pDC = GetDCEx(NULL, DCX_WINDOW | DCX_CACHE | DCX_LOCKWINDOWUPDATE);
|
|
pDC->SelectClipRgn(&rg);
|
|
CBrush* pBrush = pDC->SelectObject(CDC::GetHalftoneBrush());
|
|
pDC->PatBlt(m_rcTrack.left, m_rcTrack.top, m_rcTrack.Width(), m_rcTrack.Height(), PATINVERT);
|
|
pDC->SelectObject(pBrush);
|
|
ReleaseDC(pDC);
|
|
}
|