You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
747 lines
22 KiB
747 lines
22 KiB
//========= Copyright Valve Corporation, All rights reserved. ============// |
|
// |
|
// Purpose: Implements a dialog for showing the input connections of an entity |
|
// |
|
// $NoKeywords: $ |
|
//=============================================================================// |
|
|
|
#include "stdafx.h" |
|
#include "GlobalFunctions.h" |
|
#include "MapDoc.h" |
|
#include "MapEntity.h" |
|
#include "MapWorld.h" |
|
#include "ObjectProperties.h" |
|
#include "OP_Input.h" |
|
#include "MainFrm.h" |
|
#include "Selection.h" |
|
|
|
// memdbgon must be the last include file in a .cpp file!!! |
|
#include <tier0/memdbgon.h> |
|
|
|
// |
|
// Column indices for the list control. |
|
// |
|
const int ICON_COLUMN = 0; |
|
const int SOURCE_NAME_COLUMN = 1; |
|
const int OUTPUT_NAME_COLUMN = 2; |
|
const int INPUT_NAME_COLUMN = 3; |
|
const int PARAMETER_COLUMN = 4; |
|
const int DELAY_COLUMN = 5; |
|
const int ONLY_ONCE_COLUMN = 6; |
|
|
|
#define ICON_CONN_BAD 0 |
|
#define ICON_CONN_GOOD 1 |
|
#define ICON_CONN_BAD_GREY 2 |
|
#define ICON_CONN_GOOD_GREY 3 |
|
|
|
IMPLEMENT_DYNCREATE(COP_Input, CObjectPage) |
|
|
|
|
|
BEGIN_MESSAGE_MAP(COP_Input, CObjectPage) |
|
//{{AFX_MSG_MAP(COP_Input) |
|
ON_BN_CLICKED(IDC_MARK, OnMark) |
|
ON_WM_SIZE() |
|
ON_WM_DESTROY() |
|
//}}AFX_MSG_MAP |
|
END_MESSAGE_MAP() |
|
|
|
//----------------------------------------------------------------------------- |
|
// Static vars |
|
//----------------------------------------------------------------------------- |
|
CImageList* COP_Input::m_pImageList = NULL; |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: Constructor. |
|
//----------------------------------------------------------------------------- |
|
COP_Input::COP_Input(void) |
|
: CObjectPage(COP_Input::IDD) |
|
{ |
|
m_pObjectList = NULL; |
|
m_pEntityList = new CMapEntityList; |
|
m_pEditObjectRuntimeClass = RUNTIME_CLASS(editCMapClass); |
|
m_nSortColumn = OUTPUT_NAME_COLUMN; |
|
|
|
// |
|
// All columns initially sort in ascending order. |
|
// |
|
for (int i = 0; i < OUTPUT_LIST_NUM_COLUMNS; i++) |
|
{ |
|
m_eSortDirection[i] = Sort_Ascending; |
|
} |
|
} |
|
|
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: Destructor. |
|
//----------------------------------------------------------------------------- |
|
COP_Input::~COP_Input(void) |
|
{ |
|
// Delete my list |
|
delete m_pEntityList; |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: Compares by delays. Used as a secondary sort by all other columns. |
|
//----------------------------------------------------------------------------- |
|
static int CALLBACK InputCompareDelaysSecondary(CInputConnection *pInputConn1, CInputConnection *pInputConn2, SortDirection_t eDirection) |
|
{ |
|
CEntityConnection *pConn1 = pInputConn1->m_pConnection; |
|
CEntityConnection *pConn2 = pInputConn2->m_pConnection; |
|
return(CEntityConnection::CompareDelaysSecondary(pConn1,pConn2,eDirection)); |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: Compares by delays, does a secondary compare by output name. |
|
//----------------------------------------------------------------------------- |
|
static int CALLBACK InputCompareDelays(CInputConnection *pInputConn1, CInputConnection *pInputConn2, SortDirection_t eDirection) |
|
{ |
|
CEntityConnection *pConn1 = pInputConn1->m_pConnection; |
|
CEntityConnection *pConn2 = pInputConn2->m_pConnection; |
|
return(CEntityConnection::CompareDelays(pConn1, pConn2,eDirection)); |
|
} |
|
|
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: Compares by output name, does a secondary compare by delay. |
|
//----------------------------------------------------------------------------- |
|
static int CALLBACK InputCompareOutputNames(CInputConnection *pInputConn1, CInputConnection *pInputConn2, SortDirection_t eDirection) |
|
{ |
|
CEntityConnection *pConn1 = pInputConn1->m_pConnection; |
|
CEntityConnection *pConn2 = pInputConn2->m_pConnection; |
|
return(CEntityConnection::CompareOutputNames(pConn1,pConn2,eDirection)); |
|
} |
|
|
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: Compares by input name, does a secondary compare by delay. |
|
//----------------------------------------------------------------------------- |
|
static int CALLBACK InputCompareInputNames(CInputConnection *pInputConn1, CInputConnection *pInputConn2, SortDirection_t eDirection) |
|
{ |
|
CEntityConnection *pConn1 = pInputConn1->m_pConnection; |
|
CEntityConnection *pConn2 = pInputConn2->m_pConnection; |
|
return(CEntityConnection::CompareInputNames(pConn1,pConn2,eDirection)); |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: Compares by source name, does a secondary compare by delay. |
|
//----------------------------------------------------------------------------- |
|
static int CALLBACK InputCompareSourceNames(CInputConnection *pInputConn1, CInputConnection *pInputConn2, SortDirection_t eDirection) |
|
{ |
|
CEntityConnection *pConn1 = pInputConn1->m_pConnection; |
|
CEntityConnection *pConn2 = pInputConn2->m_pConnection; |
|
return(CEntityConnection::CompareSourceNames(pConn1,pConn2,eDirection)); |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: Compares by target name, does a secondary compare by delay. |
|
//----------------------------------------------------------------------------- |
|
static int CALLBACK InputCompareTargetNames(CInputConnection *pInputConn1, CInputConnection *pInputConn2, SortDirection_t eDirection) |
|
{ |
|
CEntityConnection *pConn1 = pInputConn1->m_pConnection; |
|
CEntityConnection *pConn2 = pInputConn2->m_pConnection; |
|
return(CEntityConnection::CompareTargetNames(pConn1,pConn2,eDirection)); |
|
} |
|
|
|
//------------------------------------------------------------------------------ |
|
// Purpose : Returns true if given item number from list control is a valid |
|
// connection type |
|
// Input : |
|
// Output : |
|
//------------------------------------------------------------------------------ |
|
bool COP_Input::ValidateConnections(int nItem) |
|
{ |
|
CInputConnection *pInputConn = (CInputConnection *)m_ListCtrl.GetItemData(nItem); |
|
|
|
// Early out |
|
if (!pInputConn) |
|
{ |
|
return false; |
|
} |
|
|
|
CEntityConnection *pConnection = pInputConn->m_pConnection; |
|
if (pConnection != NULL) |
|
{ |
|
// Validate input |
|
if (!MapEntityList_HasInput(m_pEntityList, pConnection->GetInputName())) |
|
{ |
|
return false; |
|
} |
|
|
|
// Validate output |
|
CMapEntity *pEntity = pInputConn->m_pEntity; |
|
if (!CEntityConnection::ValidateOutput(pEntity,pConnection->GetOutputName())) |
|
{ |
|
return false; |
|
} |
|
} |
|
return true; |
|
} |
|
|
|
//------------------------------------------------------------------------------ |
|
// Purpose : Updates the validity flag on the given item in the list control |
|
// Input : |
|
// Output : |
|
//------------------------------------------------------------------------------ |
|
void COP_Input::UpdateItemValidity(int nItem) |
|
{ |
|
int nIcon; |
|
if (ValidateConnections(nItem)) |
|
{ |
|
nIcon = (m_bMultipleTargetNames ? ICON_CONN_GOOD_GREY : ICON_CONN_GOOD); |
|
} |
|
else |
|
{ |
|
nIcon = (m_bMultipleTargetNames ? ICON_CONN_BAD_GREY : ICON_CONN_BAD); |
|
} |
|
m_ListCtrl.SetItem(nItem,0,LVIF_IMAGE, 0, nIcon, 0, 0, 0 ); |
|
} |
|
|
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
// Input : pEntity - |
|
// bFirst - |
|
//----------------------------------------------------------------------------- |
|
void COP_Input::AddEntityConnections(const char *pTargetName, CMapEntity *pTestEntity) |
|
{ |
|
int nConnCount = pTestEntity->Connections_GetCount(); |
|
|
|
if (nConnCount != 0) |
|
{ |
|
int nItemCount = m_ListCtrl.GetItemCount(); |
|
m_ListCtrl.SetItemCount(nItemCount + nConnCount); |
|
|
|
for (int i = 0; i < nConnCount; i++) |
|
{ |
|
CEntityConnection *pConnection = pTestEntity->Connections_Get(i); |
|
if (pConnection != NULL && !CompareEntityNames(pConnection->GetTargetName(), pTargetName)) |
|
{ |
|
// Update source name for correct sorting |
|
const char *pszTestName = pTestEntity->GetKeyValue("targetname"); |
|
if (pszTestName == NULL) |
|
{ |
|
pszTestName = pTestEntity->GetClassName(); |
|
} |
|
pConnection->SetSourceName(pszTestName); |
|
|
|
m_ListCtrl.InsertItem(LVIF_IMAGE, nItemCount, "", 0, 0, ICON_CONN_GOOD, 0); |
|
|
|
m_ListCtrl.SetItemText(nItemCount, OUTPUT_NAME_COLUMN, pConnection->GetOutputName()); |
|
m_ListCtrl.SetItemText(nItemCount, SOURCE_NAME_COLUMN, pConnection->GetSourceName()); |
|
m_ListCtrl.SetItemText(nItemCount, INPUT_NAME_COLUMN, pConnection->GetInputName()); |
|
|
|
// Build the string for the delay. |
|
float fDelay = pConnection->GetDelay(); |
|
char szTemp[MAX_PATH]; |
|
sprintf(szTemp, "%.2f", fDelay); |
|
m_ListCtrl.SetItemText(nItemCount, DELAY_COLUMN, szTemp); |
|
m_ListCtrl.SetItemText(nItemCount, ONLY_ONCE_COLUMN, (pConnection->GetTimesToFire() == EVENT_FIRE_ALWAYS) ? "No" : "Yes"); |
|
m_ListCtrl.SetItemText(nItemCount, PARAMETER_COLUMN, pConnection->GetParam()); |
|
|
|
// Set list ctrl data |
|
CInputConnection *pInputConn = new CInputConnection; |
|
pInputConn->m_pConnection = pConnection; |
|
pInputConn->m_pEntity = pTestEntity; |
|
m_ListCtrl.SetItemData(nItemCount, (DWORD)pInputConn); |
|
|
|
nItemCount++; |
|
} |
|
} |
|
} |
|
} |
|
|
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
// Input : pDX - |
|
//----------------------------------------------------------------------------- |
|
void COP_Input::DoDataExchange(CDataExchange *pDX) |
|
{ |
|
CObjectPage::DoDataExchange(pDX); |
|
|
|
//{{AFX_DATA_MAP(COP_Input) |
|
DDX_Control(pDX, IDC_LIST, m_ListCtrl); |
|
//}}AFX_DATA_MAP |
|
} |
|
|
|
//------------------------------------------------------------------------------ |
|
// Purpose : Take the user to the output page of the selected entity that |
|
// targets me. |
|
// Input : |
|
// Output : |
|
//------------------------------------------------------------------------------ |
|
void COP_Input::OnMark(void) |
|
{ |
|
// This should always be 1 as dialog is set up to be single select |
|
if (m_ListCtrl.GetSelectedCount() == 1) |
|
{ |
|
int nCount = m_ListCtrl.GetItemCount(); |
|
CMapDoc *pDoc = CMapDoc::GetActiveMapDoc(); |
|
if (nCount > 0 && pDoc) |
|
{ |
|
for (int nItem = nCount - 1; nItem >= 0; nItem--) |
|
{ |
|
if (m_ListCtrl.GetItemState(nItem, LVIS_SELECTED) & LVIS_SELECTED) |
|
{ |
|
CInputConnection *pInputConn = (CInputConnection *)m_ListCtrl.GetItemData(nItem); |
|
CMapEntity *pEntity = pInputConn->m_pEntity; |
|
CEntityConnection *pConnection = pInputConn->m_pConnection; |
|
|
|
// Shouldn't happen but just in case |
|
if (!pEntity || !pConnection) |
|
{ |
|
return; |
|
} |
|
|
|
// Switch to object selection mode so we only select the entity. |
|
pDoc->GetSelection()->SetMode(selectObjects); |
|
|
|
// Now switch to the output page with the selected connection |
|
CMapObjectList Select; |
|
Select.AddToTail(pEntity); |
|
pDoc->SelectObjectList(&Select); |
|
|
|
// (a bit squirly way of doing this) |
|
GetMainWnd()->pObjectProperties->SetPageToOutput(pConnection); |
|
pDoc->Center2DViewsOnSelection(); |
|
return; |
|
} |
|
} |
|
} |
|
} |
|
} |
|
|
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: Sets up the list view columns, initial sort column. |
|
//----------------------------------------------------------------------------- |
|
BOOL COP_Input::OnInitDialog(void) |
|
{ |
|
CObjectPage::OnInitDialog(); |
|
|
|
m_ListCtrl.SetExtendedStyle(LVS_EX_FULLROWSELECT | LVS_EX_GRIDLINES | LVS_EX_HEADERDRAGDROP); |
|
|
|
m_ListCtrl.InsertColumn(ICON_COLUMN, "", LVCFMT_CENTER, 20); |
|
m_ListCtrl.InsertColumn(SOURCE_NAME_COLUMN, "Source", LVCFMT_LEFT, 70); |
|
m_ListCtrl.InsertColumn(OUTPUT_NAME_COLUMN, "Output", LVCFMT_LEFT, 70); |
|
m_ListCtrl.InsertColumn(INPUT_NAME_COLUMN, "My Input", LVCFMT_LEFT, 70); |
|
m_ListCtrl.InsertColumn(DELAY_COLUMN, "Delay", LVCFMT_LEFT, 70); |
|
m_ListCtrl.InsertColumn(ONLY_ONCE_COLUMN, "Once", LVCFMT_LEFT, 70); |
|
m_ListCtrl.InsertColumn(PARAMETER_COLUMN, "Parameter", LVCFMT_LEFT, 70); |
|
|
|
UpdateConnectionList(); |
|
|
|
SetSortColumn(m_nSortColumn, m_eSortDirection[m_nSortColumn]); |
|
|
|
// Force an update of the column header text so that the sort indicator is shown. |
|
UpdateColumnHeaderText(m_nSortColumn, true, m_eSortDirection[m_nSortColumn]); |
|
|
|
if (m_ListCtrl.GetItemCount() > 0) |
|
{ |
|
m_ListCtrl.SetColumnWidth(OUTPUT_NAME_COLUMN, LVSCW_AUTOSIZE); |
|
m_ListCtrl.SetColumnWidth(SOURCE_NAME_COLUMN, LVSCW_AUTOSIZE); |
|
m_ListCtrl.SetColumnWidth(INPUT_NAME_COLUMN, LVSCW_AUTOSIZE); |
|
m_ListCtrl.SetColumnWidth(DELAY_COLUMN, LVSCW_AUTOSIZE_USEHEADER); |
|
m_ListCtrl.SetColumnWidth(ONLY_ONCE_COLUMN, LVSCW_AUTOSIZE_USEHEADER); |
|
m_ListCtrl.SetColumnWidth(PARAMETER_COLUMN, LVSCW_AUTOSIZE); |
|
} |
|
|
|
// Create image list. Is deleted automatically when listctrl is deleted |
|
if (!m_pImageList) |
|
{ |
|
CWinApp *pApp = AfxGetApp(); |
|
m_pImageList = new CImageList(); |
|
Assert(m_pImageList != NULL); // serious allocation failure checking |
|
m_pImageList->Create(16, 16, TRUE, 1, 0); |
|
m_pImageList->Add(pApp->LoadIcon( IDI_INPUTBAD )); |
|
m_pImageList->Add(pApp->LoadIcon( IDI_INPUT )); |
|
m_pImageList->Add(pApp->LoadIcon( IDI_INPUTBAD_GREY )); |
|
m_pImageList->Add(pApp->LoadIcon( IDI_INPUT_GREY )); |
|
} |
|
m_ListCtrl.SetImageList(m_pImageList, LVSIL_SMALL ); |
|
|
|
CAnchorDef anchorDefs[] = |
|
{ |
|
CAnchorDef( IDC_LIST, k_eSimpleAnchorAllSides ), |
|
CAnchorDef( IDC_MARK, k_eSimpleAnchorBottomSide ), |
|
CAnchorDef( IDC_INFO_TEXT, k_eSimpleAnchorBottomSide ) |
|
}; |
|
m_AnchorMgr.Init( GetSafeHwnd(), anchorDefs, ARRAYSIZE( anchorDefs ) ); |
|
|
|
return(TRUE); |
|
} |
|
|
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
// Input : wParam - |
|
// lParam - |
|
// pResult - |
|
// Output : Returns TRUE on success, FALSE on failure. |
|
//----------------------------------------------------------------------------- |
|
BOOL COP_Input::OnNotify(WPARAM wParam, LPARAM lParam, LRESULT *pResult) |
|
{ |
|
NMHDR *pnmh = (NMHDR *)lParam; |
|
|
|
if (pnmh->idFrom == IDC_LIST) |
|
{ |
|
switch (pnmh->code) |
|
{ |
|
case LVN_COLUMNCLICK: |
|
{ |
|
NMLISTVIEW *pnmv = (NMLISTVIEW *)lParam; |
|
if (pnmv->iSubItem < OUTPUT_LIST_NUM_COLUMNS) |
|
{ |
|
SortDirection_t eSortDirection = m_eSortDirection[pnmv->iSubItem]; |
|
|
|
// |
|
// If they clicked on the current sort column, reverse the sort direction. |
|
// |
|
if (pnmv->iSubItem == m_nSortColumn) |
|
{ |
|
if (m_eSortDirection[m_nSortColumn] == Sort_Ascending) |
|
{ |
|
eSortDirection = Sort_Descending; |
|
} |
|
else |
|
{ |
|
eSortDirection = Sort_Ascending; |
|
} |
|
} |
|
|
|
// |
|
// Update the sort column and sort the list. |
|
// |
|
SetSortColumn(pnmv->iSubItem, eSortDirection); |
|
} |
|
return(TRUE); |
|
} |
|
case NM_DBLCLK: |
|
{ |
|
OnMark(); |
|
return(TRUE); |
|
} |
|
} |
|
} |
|
|
|
return(CObjectPage::OnNotify(wParam, lParam, pResult)); |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: Empties the contents of the connections list control, freeing the |
|
// connection list hanging off of each row. |
|
//----------------------------------------------------------------------------- |
|
void COP_Input::RemoveAllEntityConnections(void) |
|
{ |
|
int nCount = m_ListCtrl.GetItemCount(); |
|
if (nCount > 0) |
|
{ |
|
for (int nItem = nCount - 1; nItem >= 0; nItem--) |
|
{ |
|
CInputConnection *pInputConnection = (CInputConnection *)m_ListCtrl.GetItemData(nItem); |
|
m_ListCtrl.DeleteItem(nItem); |
|
delete pInputConnection; |
|
} |
|
} |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
// Input : Mode - |
|
// pData - |
|
//----------------------------------------------------------------------------- |
|
void COP_Input::UpdateData( int Mode, PVOID pData, bool bCanEdit ) |
|
{ |
|
__super::UpdateData( Mode, pData, bCanEdit ); |
|
|
|
if (!IsWindow(m_hWnd)) |
|
{ |
|
return; |
|
} |
|
|
|
switch (Mode) |
|
{ |
|
case LoadFirstData: |
|
{ |
|
// m_ListCtrl.DeleteAllItems(); |
|
// UpdateConnectionList(); |
|
break; |
|
} |
|
|
|
case LoadData: |
|
{ |
|
// m_ListCtrl.DeleteAllItems(); |
|
// UpdateConnectionList(); |
|
|
|
break; |
|
} |
|
|
|
case LoadFinished: |
|
{ |
|
m_ListCtrl.DeleteAllItems(); |
|
UpdateConnectionList(); |
|
SortListByColumn(m_nSortColumn, m_eSortDirection[m_nSortColumn]); |
|
} |
|
} |
|
} |
|
|
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
// Input : nColumn - |
|
// eDirection - |
|
//----------------------------------------------------------------------------- |
|
void COP_Input::SetSortColumn(int nColumn, SortDirection_t eDirection) |
|
{ |
|
Assert(nColumn < OUTPUT_LIST_NUM_COLUMNS); |
|
|
|
// |
|
// If the sort column changed, update the old sort column header text. |
|
// |
|
if (m_nSortColumn != nColumn) |
|
{ |
|
UpdateColumnHeaderText(m_nSortColumn, false, eDirection); |
|
} |
|
|
|
// |
|
// If the sort column or direction changed, update the new sort column header text. |
|
// |
|
if ((m_nSortColumn != nColumn) || (m_eSortDirection[m_nSortColumn] != eDirection)) |
|
{ |
|
UpdateColumnHeaderText(nColumn, true, eDirection); |
|
} |
|
|
|
m_nSortColumn = nColumn; |
|
m_eSortDirection[m_nSortColumn] = eDirection; |
|
|
|
SortListByColumn(m_nSortColumn, m_eSortDirection[m_nSortColumn]); |
|
} |
|
|
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: Sorts the outputs list by column. |
|
// Input : nColumn - Index of column by which to sort. |
|
//----------------------------------------------------------------------------- |
|
void COP_Input::SortListByColumn(int nColumn, SortDirection_t eDirection) |
|
{ |
|
PFNLVCOMPARE pfnSort = NULL; |
|
|
|
switch (nColumn) |
|
{ |
|
case ONLY_ONCE_COLUMN: |
|
{ |
|
// No sort |
|
break; |
|
} |
|
|
|
case PARAMETER_COLUMN: |
|
{ |
|
// No sort |
|
break; |
|
} |
|
case OUTPUT_NAME_COLUMN: |
|
{ |
|
pfnSort = (PFNLVCOMPARE)InputCompareOutputNames; |
|
break; |
|
} |
|
|
|
case SOURCE_NAME_COLUMN: |
|
{ |
|
pfnSort = (PFNLVCOMPARE)InputCompareSourceNames; |
|
break; |
|
} |
|
|
|
case INPUT_NAME_COLUMN: |
|
{ |
|
pfnSort = (PFNLVCOMPARE)InputCompareInputNames; |
|
break; |
|
} |
|
|
|
case DELAY_COLUMN: |
|
{ |
|
pfnSort = (PFNLVCOMPARE)InputCompareDelays; |
|
break; |
|
} |
|
|
|
default: |
|
{ |
|
Assert(FALSE); |
|
break; |
|
} |
|
} |
|
|
|
if (pfnSort != NULL) |
|
{ |
|
m_ListCtrl.SortItems(pfnSort, (DWORD)eDirection); |
|
} |
|
} |
|
|
|
//------------------------------------------------------------------------------ |
|
// Purpose : Generates list of map entites that are being edited from the |
|
// m_pObject list |
|
// Input : |
|
// Output : |
|
//------------------------------------------------------------------------------ |
|
void COP_Input::UpdateEntityList() |
|
{ |
|
// Clear old entity list |
|
m_pEntityList->RemoveAll(); |
|
|
|
if (m_pObjectList != NULL) |
|
{ |
|
FOR_EACH_OBJ( *m_pObjectList, pos ) |
|
{ |
|
CMapClass *pObject = m_pObjectList->Element(pos); |
|
|
|
if ((pObject != NULL) && (pObject->IsMapClass(MAPCLASS_TYPE(CMapEntity)))) |
|
{ |
|
CMapEntity *pEntity = (CMapEntity *)pObject; |
|
m_pEntityList->AddToTail(pEntity); |
|
} |
|
} |
|
} |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
//----------------------------------------------------------------------------- |
|
void COP_Input::UpdateConnectionList(void) |
|
{ |
|
UpdateEntityList(); |
|
RemoveAllEntityConnections(); |
|
m_bMultipleTargetNames = false; |
|
|
|
const char *pszTargetName = NULL; |
|
|
|
FOR_EACH_OBJ( *m_pEntityList, pos ) |
|
{ |
|
CMapEntity *pInEntity = m_pEntityList->Element(pos); |
|
|
|
if (!pszTargetName) |
|
{ |
|
pszTargetName = pInEntity->GetKeyValue("targetname"); |
|
} |
|
else if (pszTargetName != pInEntity->GetKeyValue("targetname")) |
|
{ |
|
pszTargetName = pInEntity->GetKeyValue("targetname"); |
|
m_bMultipleTargetNames = true; |
|
} |
|
|
|
if (pszTargetName) |
|
{ |
|
CMapDoc *pDoc = CMapDoc::GetActiveMapDoc(); |
|
CMapWorld *pWorld = pDoc->GetMapWorld(); |
|
const CMapEntityList *pEntityList = pWorld->EntityList_GetList(); |
|
|
|
FOR_EACH_OBJ( *pEntityList, pos2 ) |
|
{ |
|
CMapEntity *pTestEntity = pEntityList->Element(pos2); |
|
if (pTestEntity != NULL) |
|
{ |
|
AddEntityConnections(pszTargetName, pTestEntity); |
|
} |
|
} |
|
} |
|
} |
|
|
|
// Update validity flag on all items |
|
for (int nItem = 0; nItem < m_ListCtrl.GetItemCount(); nItem++) |
|
{ |
|
UpdateItemValidity(nItem); |
|
} |
|
|
|
m_ListCtrl.EnableWindow(true); |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: Adds or removes the little 'V' or '^' sort indicator as appropriate. |
|
// Input : nColumn - Index of column to update. |
|
// bSortColumn - true if this column is the sort column, false if not. |
|
// eDirection - Direction of sort, Sort_Ascending or Sort_Descending. |
|
//----------------------------------------------------------------------------- |
|
void COP_Input::UpdateColumnHeaderText(int nColumn, bool bIsSortColumn, SortDirection_t eDirection) |
|
{ |
|
char szHeaderText[MAX_PATH]; |
|
|
|
LVCOLUMN Column; |
|
memset(&Column, 0, sizeof(Column)); |
|
Column.mask = LVCF_TEXT; |
|
Column.pszText = szHeaderText; |
|
Column.cchTextMax = sizeof(szHeaderText); |
|
m_ListCtrl.GetColumn(nColumn, &Column); |
|
|
|
int nMarker = 0; |
|
|
|
if (szHeaderText[0] != '\0') |
|
{ |
|
nMarker = strlen(szHeaderText) - 1; |
|
char chMarker = szHeaderText[nMarker]; |
|
|
|
if ((chMarker == '>') || (chMarker == '<')) |
|
{ |
|
nMarker -= 2; |
|
} |
|
else |
|
{ |
|
nMarker++; |
|
} |
|
} |
|
|
|
if (bIsSortColumn) |
|
{ |
|
if (nMarker != 0) |
|
{ |
|
szHeaderText[nMarker++] = ' '; |
|
szHeaderText[nMarker++] = ' '; |
|
} |
|
|
|
szHeaderText[nMarker++] = (eDirection == Sort_Ascending) ? '>' : '<'; |
|
} |
|
|
|
szHeaderText[nMarker] = '\0'; |
|
|
|
m_ListCtrl.SetColumn(nColumn, &Column); |
|
} |
|
|
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: Called when our window is being destroyed. |
|
//----------------------------------------------------------------------------- |
|
void COP_Input::OnDestroy(void) |
|
{ |
|
RemoveAllEntityConnections(); |
|
} |
|
|
|
//------------------------------------------------------------------------------ |
|
// Purpose: Set the selected item in the listbox |
|
// Input : pConnection |
|
//------------------------------------------------------------------------------ |
|
void COP_Input::SetSelectedConnection(CEntityConnection *pConnection) |
|
{ |
|
m_ListCtrl.SetRedraw(FALSE); |
|
|
|
// Set selected item to be active and all others to false |
|
int nItemCount = m_ListCtrl.GetItemCount(); |
|
for (int nItem = 0; nItem < nItemCount; nItem++) |
|
{ |
|
CInputConnection *pOutputConn = (CInputConnection *)m_ListCtrl.GetItemData(nItem); |
|
|
|
if ( pOutputConn->m_pConnection == pConnection) |
|
{ |
|
m_ListCtrl.SetItemState(nItem,LVIS_SELECTED,LVIS_SELECTED); |
|
} |
|
else |
|
{ |
|
m_ListCtrl.SetItemState(nItem, (unsigned int)~LVIS_SELECTED, (unsigned int)LVIS_SELECTED); |
|
} |
|
} |
|
|
|
m_ListCtrl.SetRedraw(TRUE); |
|
} |
|
|
|
void COP_Input::OnSize( UINT nType, int cx, int cy ) |
|
{ |
|
m_AnchorMgr.OnSize(); |
|
} |
|
|
|
|
|
|