Windows NT 4.0 source code leak
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.
 
 
 
 
 
 

1038 lines
24 KiB

//
// director.cpp : implementation file
//
#include "stdafx.h"
#include "comprop.h"
#include "ipaddr.hpp"
#include "dirpropd.h"
//
// Column width relative weights
//
#define WT_DIRECTORY 4
#define WT_ALIAS 2
#define WT_IPADDRESS 2
#define WT_ERRORS 3
extern "C"
{
#include <lm.h>
}
#ifdef _DEBUG
#undef THIS_FILE
static char BASED_CODE THIS_FILE[] = __FILE__;
#endif
#define THIS_PAGE_IS_COMMON FALSE
//
// CDirectoriesListBox : a listbox of CDirEntry structures
//
IMPLEMENT_DYNAMIC(CDirectoriesListBox, CListBoxEx);
const int CDirectoriesListBox::nBitmaps = 3;
CDirectoriesListBox::CDirectoriesListBox(
UINT nHomeDir, // String ID for <Home Directory> string
int * pnTabs // Array of tabs
)
{
if (pnTabs != NULL)
{
SetTabs(pnTabs);
}
VERIFY(m_strHomeDirectory.LoadString(nHomeDir));
}
BOOL
CDirectoriesListBox::ComputeTabs(
int nIndex,
int & nTab1,
int & nTab2
) const
{
if (m_anTabs[nIndex] > 0)
{
nTab1 = 0;
for (int n = 0; n < nIndex; ++n)
{
nTab1 += m_anTabs[n];
}
nTab2 = nTab1 + m_anTabs[nIndex];
return TRUE;
}
return FALSE;
}
void
CDirectoriesListBox::DrawItemEx(
CListBoxExDrawStruct& ds
)
{
CDirEntry * p = (CDirEntry *)ds.m_ItemData;
ASSERT(p != NULL);
CDC * pBmpDC = (CDC *)&ds.m_pResources->DcBitMap();
int bmh = ds.m_pResources->BitmapHeight();
int bmw = ds.m_pResources->BitmapWidth();
int nTab1, nTab2;
//
// Display a home directory bitmap
//
if (ComputeTabs(HI_DIRECTORY, nTab1, nTab2))
{
//
// Make sure there's room for the bitmap
//
if (m_anTabs[HI_DIRECTORY] > bmw)
{
int bm_h = (ds.m_Sel) ? 0 : bmh;
int bm_w = p->IsHome() ? 0 : (2 * bmw);
ds.m_pDC->BitBlt( ds.m_Rect.left+1, ds.m_Rect.top, bmw, bmh,
pBmpDC, bm_w, bm_h, SRCCOPY );
}
ColumnText(ds.m_pDC, ds.m_Rect.left + bmw + 3, ds.m_Rect.top, nTab2,
ds.m_Rect.bottom, p->QueryDirectory());
}
if (ComputeTabs(HI_ALIAS, nTab1, nTab2))
{
CString strAlias;
if (p->IsHome())
{
strAlias = m_strHomeDirectory;
}
else
{
strAlias = p->QueryAlias();
}
ColumnText(ds.m_pDC, ds.m_Rect.left + nTab1, ds.m_Rect.top,
nTab2, ds.m_Rect.bottom, strAlias);
}
if (ComputeTabs(HI_IPADDRESS, nTab1, nTab2))
{
CIpAddress ia(p->QueryIpAddress());
if ((LONG)ia != 0L)
{
ColumnText(ds.m_pDC, ds.m_Rect.left + nTab1, ds.m_Rect.top,
nTab2, ds.m_Rect.bottom, ia);
}
}
if (ComputeTabs(HI_ERRORS, nTab1, nTab2))
{
#define MAX_ERROR 255
DWORD dwError= p->QueryError();
if (dwError != ERROR_SUCCESS)
{
CString strError;
GetSystemMessage(dwError,
strError.GetBuffer(MAX_ERROR), MAX_ERROR);
strError.ReleaseBuffer();
if (m_anTabs[HI_ERRORS] > bmw)
{
int bm_h = (ds.m_Sel) ? 0 : bmh;
int bm_w = bmw;
ds.m_pDC->BitBlt( ds.m_Rect.left + nTab1, ds.m_Rect.top, bmw, bmh,
pBmpDC, bm_w, bm_h, SRCCOPY );
}
ColumnText(ds.m_pDC, ds.m_Rect.left + bmw + nTab1, ds.m_Rect.top,
nTab2, ds.m_Rect.bottom, strError);
}
}
}
//
// DirectoryPage property page
//
IMPLEMENT_DYNCREATE(DirectoryPage, INetPropertyPage)
DirectoryPage::DirectoryPage(
INetPropertySheet * pSheet,
BOOL fUseTCPIP,
BOOL fErrorColumn,
DWORD dwMask
)
: INetPropertyPage(DirectoryPage::IDD, pSheet,
::GetModuleHandle(COMPROP_DLL_NAME)),
m_list_Directories(
IDS_HOME_DIRECTORY,
0
),
m_ListBoxRes(
IDB_HOME,
m_list_Directories.nBitmaps
),
m_oblDirectories(),
m_nSortColumn(HI_DIRECTORY),
m_fDisplayErrorColumn(fErrorColumn),
m_fUseTCPIP(fUseTCPIP),
m_dwAccessMask(dwMask)
{
//{{AFX_DATA_INIT(DirectoryPage)
//}}AFX_DATA_INIT
m_list_Directories.AttachResources( &m_ListBoxRes );
}
DirectoryPage::~DirectoryPage()
{
//
// The directories oblist will clean itself up
//
}
void
DirectoryPage::DoDataExchange(
CDataExchange* pDX
)
{
INetPropertyPage::DoDataExchange(pDX);
//{{AFX_DATA_MAP(DirectoryPage)
DDX_Control(pDX, IDC_ADD, m_button_Add);
DDX_Control(pDX, IDC_REMOVE, m_button_Remove);
DDX_Control(pDX, IDC_BUTTON_EDIT, m_button_Edit);
//}}AFX_DATA_MAP
DDX_Control(pDX, IDC_LIST_DIRECTORIES, m_list_Directories);
}
BEGIN_MESSAGE_MAP(DirectoryPage, INetPropertyPage)
//{{AFX_MSG_MAP(DirectoryPage)
ON_BN_CLICKED(IDC_REMOVE, OnRemove)
ON_BN_CLICKED(IDC_BUTTON_EDIT, OnButtonEdit)
ON_BN_CLICKED(IDC_ADD, OnAdd)
ON_LBN_DBLCLK(IDC_LIST_DIRECTORIES, OnDblclkListDirectories)
ON_LBN_SELCHANGE(IDC_LIST_DIRECTORIES, OnSelchangeListDirectories)
ON_LBN_ERRSPACE(IDC_LIST_DIRECTORIES, OnErrspaceListDirectories)
ON_WM_VKEYTOITEM()
//}}AFX_MSG_MAP
ON_NOTIFY_RANGE( HDN_ENDTRACK, 0, 0xFFFF, OnHeaderEndTrack )
ON_NOTIFY_RANGE( HDN_ITEMCLICK, 0, 0xFFFF, OnHeaderItemClick )
END_MESSAGE_MAP()
//
// Set the edit/remove button states depending on
// whether anything is selected in the listbox.
//
void
DirectoryPage::SetControlStates()
{
BOOL fSelection = m_list_Directories.GetCurSel() != -1;
m_button_Remove.EnableWindow(fSelection);
m_button_Edit.EnableWindow(fSelection);
}
//
// Display the add/edit dialog. The return
// value is the value returned by the dialog
//
int
DirectoryPage::ShowPropertyDialog(
BOOL fAdd
)
{
CDirEntry dir; // Empty object for adding
CDirEntry * pDir = NULL;
int nCurSel = LB_ERR;
if (!fAdd)
{
nCurSel = m_list_Directories.GetCurSel();
if (nCurSel != LB_ERR)
{
//
// Get directory properties
//
pDir = m_list_Directories.GetItem(nCurSel);
}
}
else
{
//
// Point to the empty directory entry
//
pDir = &dir;
}
ASSERT(pDir != NULL);
CDirPropDlg dlgDirProp(*pDir, &m_oblDirectories,
IsLocal(), fAdd, m_fUseTCPIP, m_dwAccessMask, this,
IDD_DIRECTORY_PROPERTIES, GetSheet()->IsVer3OrAbove());
int nReturn = dlgDirProp.DoModal();
if (nReturn == IDOK)
{
//
// When editing, delete and re-add (to make sure the
// list is properly sorted)
//
if (!fAdd)
{
m_oblDirectories.RemoveIndex(nCurSel);
}
//
// The check for duplicate home directories will
// already have been made in the directory properties
// dialog, and if we get to this point, any existing
// home directories will already have an alias name
// generated for it.
//
m_oblDirectories.AddTail(new CDirEntry(dlgDirProp.QueryDirEntry()));
switch(QuerySortColumn())
{
case HI_DIRECTORY:
SortByDirectory();
break;
case HI_ALIAS:
SortByAlias();
break;
case HI_IPADDRESS:
SortByAddress();
break;
case HI_ERRORS:
SortByError();
break;
}
FillListBox();
}
return nReturn;
}
//
// Given the column number, obtain the
// index in our directory column array
//
int
DirectoryPage::MapColumnToIndex(
int nCol
) const
{
ASSERT(nCol >= 0 && nCol < HI_NUM_COLUMNS);
int nIndex = -1;
for (int n = 0; n < HI_NUM_COLUMNS; ++n)
{
if (m_anColumns[n] != -1)
{
++nIndex;
}
if (nIndex == nCol)
{
return n;
}
}
//
// This should never happen!
//
ASSERT(0);
return -1;
}
//
// Ensure that the two columns take up the entire width
// of the control, by changing the size of the second
// column.
//
void
DirectoryPage::AdjustColumns(
HD_NOTIFY * pNotify // Or NULL
)
{
HD_ITEM hdi;
int nTabs[HI_NUM_COLUMNS];
hdi.mask = HDI_WIDTH;
for (int i = 0; i < HI_NUM_COLUMNS; ++i)
{
if (m_anColumns[i] == -1)
{
nTabs[i] = -1;
}
else
{
VERIFY(m_hdr.GetItem(m_anColumns[i], &hdi));
nTabs[i] = hdi.cxy;
}
}
//
// Adjust for what was just dragged, since the size
// isn't updated until after we get the end-tracking
// message (btw this is highly annoying)
//
if (pNotify != NULL)
{
ASSERT(pNotify->pitem->mask & HDI_WIDTH);
ASSERT(pNotify->iItem >= 0 && pNotify->iItem < HI_NUM_COLUMNS);
nTabs[MapColumnToIndex(pNotify->iItem)] = pNotify->pitem->cxy;
}
m_list_Directories.SetTabs(nTabs);
}
//
// Populate the listbox with the directory
// entries
//
void
DirectoryPage::FillListBox()
{
CObListIter obli( m_oblDirectories );
const CDirEntry * pDirEntry;
//
// Remember the selection.
//
int nCurSel = m_list_Directories.GetCurSel();
m_list_Directories.SetRedraw(FALSE);
m_list_Directories.ResetContent();
int cItems = 0;
for ( /**/ ; pDirEntry = (CDirEntry *) obli.Next() ; cItems++ )
{
m_list_Directories.AddString( (LPCTSTR)pDirEntry );
}
m_list_Directories.SetRedraw(TRUE);
m_list_Directories.SetCurSel(nCurSel);
}
//
// Sorting the directory list by the directories names
// FillListBox() should be called after this because
// the listbox will no longer reflect the true status
// of the list of directories.
//
LONG
DirectoryPage::SortByDirectory()
{
m_nSortColumn = HI_DIRECTORY;
if (m_oblDirectories.GetCount() < 2)
{
//
// Don't bother
//
return 0;
}
BeginWaitCursor();
LONG l = m_oblDirectories.Sort(
(CObjectPlus::PCOBJPLUS_ORDER_FUNC) &CDirEntry::OrderByDirectory );
EndWaitCursor();
return l;
}
//
// As above, but sort by the alias names of the directories
//
LONG
DirectoryPage::SortByAlias()
{
m_nSortColumn = HI_ALIAS;
if (m_oblDirectories.GetCount() < 2)
{
//
// Don't bother
//
return 0;
}
BeginWaitCursor();
LONG l = m_oblDirectories.Sort(
(CObjectPlus::PCOBJPLUS_ORDER_FUNC) & CDirEntry::OrderByAlias );
EndWaitCursor();
return l;
}
//
// As above, but sort by the ip address of the directories
//
LONG
DirectoryPage::SortByAddress()
{
m_nSortColumn = HI_IPADDRESS;
if (m_oblDirectories.GetCount() < 2)
{
//
// Don't bother
//
return 0;
}
BeginWaitCursor();
LONG l = m_oblDirectories.Sort(
(CObjectPlus::PCOBJPLUS_ORDER_FUNC) & CDirEntry::OrderByIpAddress );
EndWaitCursor();
return l;
}
//
// As above, but sort by the error value of the directories
//
LONG
DirectoryPage::SortByError()
{
m_nSortColumn = HI_ERRORS;
if (m_oblDirectories.GetCount() < 2)
{
//
// Don't bother
//
return 0;
}
BeginWaitCursor();
LONG l = m_oblDirectories.Sort(
(CObjectPlus::PCOBJPLUS_ORDER_FUNC) & CDirEntry::OrderByError );
EndWaitCursor();
return l;
}
//
// Insert column. The width of the column is actually
// a relative "weight" of the column which needs to
// be adjusted later. The return value is the column
// number or -1 if the column is not inserted
//
int
DirectoryPage::InsertColumn(
BOOL fCondition, // Insert if TRUE
int & nCol, // Column number
int nWeight, // Relative weight of column
int & nTotalWeight, // Total weight
UINT nStringID // Resource string ID
)
{
if (fCondition)
{
CString strDirName;
HD_ITEM hdItem;
VERIFY(strDirName.LoadString(nStringID));
hdItem.mask = HDI_FORMAT | HDI_WIDTH | HDI_TEXT;
hdItem.fmt = HDF_STRING | HDF_LEFT;
hdItem.pszText = (LPTSTR)(LPCTSTR)strDirName;
hdItem.cchTextMax = strDirName.GetLength();
nTotalWeight += (hdItem.cxy = nWeight);
return m_hdr.InsertItem(nCol++, &hdItem);
}
return -1;
}
//
// Convert weighted column width to actual width.
//
void
DirectoryPage::ConvertColumnWidth(
int nCol,
int nTotalWeight,
int nTotalWidth
)
{
if (nCol >= 0)
{
HD_ITEM hdItem;
hdItem.mask = HDI_WIDTH;
VERIFY(m_hdr.GetItem(nCol, &hdItem));
ASSERT(hdItem.cxy > 0);
hdItem.cxy = nTotalWidth * hdItem.cxy / nTotalWeight;
VERIFY(m_hdr.SetItem(nCol, &hdItem));
}
}
//
// DirectoryPage message handlers
//
BOOL
DirectoryPage::OnInitDialog()
{
INetPropertyPage::OnInitDialog();
RECT rc;
::GetDlgCtlRect(this->m_hWnd, m_list_Directories.m_hWnd, &rc);
//
// Create a header control just above the listbox. Set
// the width equal to the width of the listbox, and
// set the height equal to 7/8 the height of the edit
// button.
//
RECT rcButn;
m_button_Edit.GetClientRect(&rcButn);
rc.bottom = rc.top;
rc.top -= 7 * rcButn.bottom / 8;
int nWidth = rc.right - rc.left + 1;
m_hdr.Create( WS_VISIBLE | WS_CHILD | WS_BORDER
| HDS_BUTTONS | HDS_HORZ, rc, this, IDC_HEADER );
int nTotalWeight = 0;
int nCol = 0;
m_anColumns[HI_DIRECTORY] = InsertColumn(TRUE, nCol, WT_DIRECTORY,
nTotalWeight, IDS_DIRECTORY);
m_anColumns[HI_ALIAS] = InsertColumn(TRUE, nCol, WT_ALIAS, nTotalWeight,
IDS_ALIAS);
m_anColumns[HI_IPADDRESS] = InsertColumn(m_fUseTCPIP, nCol, WT_IPADDRESS,
nTotalWeight, IDS_IPADDRESS);
m_anColumns[HI_ERRORS] = InsertColumn(m_fDisplayErrorColumn, nCol, WT_ERRORS,
nTotalWeight, IDS_ERROR);
for (nCol = 0; nCol < HI_NUM_COLUMNS; ++nCol)
{
ConvertColumnWidth(m_anColumns[nCol], nTotalWeight, nWidth);
}
#ifdef NO_LSA
m_button_Add.EnableWindow(FALSE);
m_button_Remove.EnableWindow(FALSE);
m_button_Edit.EnableWindow(FALSE);
m_hdr.EnableWindow(FALSE);
m_list_Directories.EnableWindow(FALSE);
#else
TRY
{
if ( SingleServerSelected()
&& QueryConfigError() == ERROR_SUCCESS
&& GetInetConfigData()->VirtualRoots != NULL
)
{
for (DWORD i = 0; i < GetInetConfigData()->VirtualRoots->cEntries; i++)
{
CDirEntry * pDirEntry = new CDirEntry(
GetInetConfigData()->VirtualRoots->aVirtRootEntry[i].pszDirectory,
GetInetConfigData()->VirtualRoots->aVirtRootEntry[i].pszRoot,
GetInetConfigData()->VirtualRoots->aVirtRootEntry[i].pszAccountName,
GetInetConfigData()->VirtualRoots->aVirtRootEntry[i].AccountPassword,
GetInetConfigData()->VirtualRoots->aVirtRootEntry[i].pszAddress,
GetInetConfigData()->VirtualRoots->aVirtRootEntry[i].dwMask,
GetInetConfigData()->VirtualRoots->aVirtRootEntry[i].dwError
);
ASSERT(pDirEntry != NULL);
if (pDirEntry->IsHome())
{
int nSel;
CIpAddress ipaTarget = pDirEntry->QueryIpAddress();
if (::FindExistingHome(ipaTarget, m_oblDirectories, nSel))
{
//
// We already had a home dir for this ip -- can't have that
//
TRACEEOLID(_T("Duplicate home directories found for this ip address."));
::AfxMessageBox(IDS_WRN_MULTIPLE_HOMES,
MB_ICONINFORMATION | MB_OK);
pDirEntry->GenerateAutoAlias();
}
}
m_oblDirectories.AddTail(pDirEntry);
}
SortByDirectory();
FillListBox();
}
}
CATCH_ALL(e)
{
TRACEEOLID(_T("Exception in DirectoryPage::OnInitDialog() -- bailing out"));
::DisplayMessage(::GetLastError());
EndDialog(IDCANCEL);
return FALSE;
}
END_CATCH_ALL
#endif // NO_LSA
AdjustColumns();
SetControlStates();
return FALSE; // return TRUE unless you set the focus to a control
// EXCEPTION: OCX Property Pages should return FALSE
}
//
// "Apply now" or "OK" has been pressed. Save our stuff
// in the registry.
//
NET_API_STATUS
DirectoryPage::SaveInfo(
BOOL fUpdateData
)
{
if (!IsDirty() || (fUpdateData && !UpdateData(TRUE)))
{
return NO_ERROR;
}
TRACEEOLID(_T("Saving directory page now..."));
NET_API_STATUS err = 0;
#ifndef NO_LSA
CInetAConfigInfo config(GetConfig());
LPINETA_VIRTUAL_ROOT_LIST lpVirtualRoots = GetRoots();
if (lpVirtualRoots == NULL)
{
return ::GetLastError();
}
config.SetValues(
lpVirtualRoots
);
err = config.SetInfo(THIS_PAGE_IS_COMMON);
//
// Clean up
//
DestroyRoots(lpVirtualRoots);
#endif // NO_LSA
SetModified(FALSE);
return err;
}
//
// Build root table from private directory list
//
LPINETA_VIRTUAL_ROOT_LIST
DirectoryPage::GetRoots()
{
int cListItems = m_oblDirectories.GetCount();
DWORD cbNeeded = sizeof(INETA_VIRTUAL_ROOT_LIST) +
(sizeof(INETA_VIRTUAL_ROOT_ENTRY) * cListItems);;
LPINETA_VIRTUAL_ROOT_LIST pItemList = NULL;
int cItems;
TRY
{
TRACEEOLID(_T("Attempting to allocate rootlist of ") << cbNeeded
<< _T(" bytes"));
pItemList = (LPINETA_VIRTUAL_ROOT_LIST)new BYTE[cbNeeded];
ASSERT(pItemList);
//
// This shouldn't be necessary, but I tend
// to be paranoid about this sort of thing
//
::memset(pItemList, 0, cbNeeded);
pItemList->cEntries = cListItems;
CObListIter obli( m_oblDirectories );
const CDirEntry * pDirEntry;
cItems = 0;
for ( /**/ ; pDirEntry = (CDirEntry *) obli.Next() ; cItems++ )
{
TRACEEOLID(_T("Adding directory entry ") << cItems );
//
// Only fill in the IP address if the entry
// has a valid one. Otherwise, this will
// be a blank string.
//
CString strIpAddress;
if (pDirEntry->HasIPAddress())
{
strIpAddress = (CString)pDirEntry->QueryIpAddress();
}
ASSERT(strIpAddress.GetLength() <= 15); // xxx.xxx.xxx.xxx
pItemList->aVirtRootEntry[cItems].dwMask = pDirEntry->QueryMask();
::TextToText(pItemList->aVirtRootEntry[cItems].pszDirectory,
pDirEntry->QueryDirectory());
::TextToText(pItemList->aVirtRootEntry[cItems].pszRoot,
pDirEntry->QueryAlias());
::TextToText(pItemList->aVirtRootEntry[cItems].pszAccountName,
pDirEntry->QueryUserName());
::TextToText(pItemList->aVirtRootEntry[cItems].pszAddress,
strIpAddress);
TWSTRCPY(pItemList->aVirtRootEntry[cItems].AccountPassword,
pDirEntry->QueryPassword(),
STRSIZE(pItemList->aVirtRootEntry[cItems].AccountPassword));
TRACEEOLID(_T("password = ")
<< pItemList->aVirtRootEntry[cItems].AccountPassword);
TRACEEOLID(_T("directory = ")
<< pItemList->aVirtRootEntry[cItems].pszDirectory);
TRACEEOLID(_T("root = ")
<< pItemList->aVirtRootEntry[cItems].pszRoot);
TRACEEOLID(_T("account name = ")
<< pItemList->aVirtRootEntry[cItems].pszAccountName);
TRACEEOLID(_T("Address = ")
<< pItemList->aVirtRootEntry[cItems].pszAddress);
TRACEEOLID(_T("--"));
}
}
CATCH_ALL(e)
{
TRACEEOLID(_T("Exception in DirectoryPage::GetRoots() -- bailing out"));
return NULL;
}
END_CATCH_ALL
//
// We should have added everything by now...
//
ASSERT(cItems == cListItems);
return pItemList;
}
//
// Destroy root list
//
void
DirectoryPage::DestroyRoots(
LPINETA_VIRTUAL_ROOT_LIST & pItemList
)
{
if (pItemList != NULL)
{
TRACEEOLID(_T("Destroying vroot list. Size of list = ")
<< pItemList->cEntries );
for (DWORD i = 0; i < pItemList->cEntries; ++i)
{
TRACEEOLID(_T("Destroying item #") << i);
delete pItemList->aVirtRootEntry[i].pszDirectory;
delete pItemList->aVirtRootEntry[i].pszRoot;
delete pItemList->aVirtRootEntry[i].pszAccountName;
delete pItemList->aVirtRootEntry[i].pszAddress;
}
delete pItemList;
pItemList = NULL;
}
}
//
// Remove the currently selected directory
// entry
//
void
DirectoryPage::OnRemove()
{
//
// First get current selection
//
int nCurSel = m_list_Directories.GetCurSel();
if (nCurSel != LB_ERR)
{
//
// ISSUE: Do we ask for validation?
//
m_oblDirectories.RemoveIndex(nCurSel);
m_list_Directories.DeleteString(nCurSel);
if (nCurSel)
{
--nCurSel;
}
m_list_Directories.SetCurSel(nCurSel);
SetControlStates();
SetModified(TRUE);
}
}
//
// Edit currently selected directory
//
void
DirectoryPage::OnButtonEdit()
{
if (ShowPropertyDialog(FALSE) == IDOK)
{
SetControlStates();
SetModified(TRUE);
}
}
//
// Add new directory entry
//
void
DirectoryPage::OnAdd()
{
if (ShowPropertyDialog(TRUE) == IDOK)
{
SetControlStates();
SetModified(TRUE);
}
}
//
// Message received when finished
// resizing the column widths with the
// header control
//
void
DirectoryPage::OnHeaderEndTrack(
UINT nId,
NMHDR *n,
LRESULT *l
)
{
//
// Make sure columns take up whole width of the
// list view
//
HD_NOTIFY *pNotify = (HD_NOTIFY *)n;
if ( pNotify->pitem->mask & HDI_WIDTH )
{
m_list_Directories.SetRedraw(FALSE);
AdjustColumns(pNotify);
m_list_Directories.SetRedraw(TRUE);
m_list_Directories.Invalidate();
}
}
//
// A button has been clicked in the header control
//
void
DirectoryPage::OnHeaderItemClick(
UINT nId,
NMHDR *n,
LRESULT *l
)
{
HD_NOTIFY *pNotify = (HD_NOTIFY *)n;
TRACEEOLID(_T("Header Button clicked."));
//
// Can't press a button out of range, surely...
//
ASSERT(pNotify->iItem < m_hdr.GetItemCount());
int nIndex = MapColumnToIndex(pNotify->iItem);
switch(nIndex)
{
case HI_DIRECTORY:
SortByDirectory();
break;
case HI_ALIAS:
SortByAlias();
break;
case HI_IPADDRESS:
SortByAddress();
break;
case HI_ERRORS:
SortByError();
break;
default:
TRACEEOLID(_T("Invalid column number ignored"));
}
FillListBox();
SetControlStates();
}
//
// Double-click means edit the currently selected
// entry.
//
void
DirectoryPage::OnDblclkListDirectories()
{
OnButtonEdit();
}
void
DirectoryPage::OnSelchangeListDirectories()
{
SetControlStates();
}
void
DirectoryPage::OnErrspaceListDirectories()
{
SetControlStates();
}
int
DirectoryPage::OnVKeyToItem(
UINT nKey,
CListBox* pListBox,
UINT nIndex
)
{
switch(nKey)
{
case VK_DELETE:
OnRemove();
break;
case VK_INSERT:
OnAdd();
break;
default:
//
// Not completely handled by this function, let
// windows handle the remaining default action.
//
return -1;
}
//
// No further action is neccesary.
//
return -2;
}