|
|
///////////////////////////////////////////////////////////
//
//
// HHFinder.cpp : Implementation of CHHFinder
//
//
#include "header.h"
#ifdef _DEBUG
#undef THIS_FILE
static const CHAR THIS_FILE[] = __FILE__; #endif
#include "resource.h"
#include "strtable.h"
#include "atlinc.h" // includes for ATL.
#include "HHFinder.h"
#include "cdlg.h"
#include "wwheel.h"
#include "secwin.h"
// Used to lock toplevel windows before displaying a dialog.
#include "lockout.h"
// defines
#define HH_VERSION_1_3 // define this is build HH 1.3 or newer
///////////////////////////////////////////////////////////
//
// Internal Structure Definition
//
///////////////////////////////////////////////////////////
//
// HHREMOVEABLE
//
typedef struct _hhremovable { UINT uiDriveType; PCSTR pszDriveLetter; PCSTR pszVolumeName; PSTR* ppszLocation; } HHREMOVABLE;
///////////////////////////////////////////////////////////
//
// Globals
//
#ifdef _DEBUG
static BOOL g_bShowMessage = TRUE; #endif
///////////////////////////////////////////////////////////
//
// Prototypes
//
INT_PTR CALLBACK RemovableMediaDialogProc( HWND hDlg, UINT uMsg, WPARAM wParam, LPARAM lParam );
///////////////////////////////////////////////////////////
//
// Functions
//
///////////////////////////////////////////////////////////
//
// GetPathAndFileName
//
PCSTR GetPathAndFileName( PCSTR pszFilename, PSTR pszPathBuffer, PSTR pszFilenameBuffer ) { CHAR szPathname[MAX_PATH]; PSTR pszFile; GetFullPathName( pszFilename, sizeof(szPathname), szPathname, &pszFile ); lstrcpyn( pszPathBuffer, szPathname, (int)(((DWORD_PTR)pszFile) - ((DWORD_PTR)&szPathname)) ); strcpy( pszFilenameBuffer, pszFile );
return( pszFilename ); }
/////////////////////////////////////////////////////////////////////////////
// CLocationNode
class CLocationNode { public: CLocationNode::CLocationNode( PCSTR pszLocationId ) { m_pszLocationId = new CHAR[strlen(pszLocationId)+1]; strcpy( (PSTR) m_pszLocationId, pszLocationId ); m_pNext = NULL; } CLocationNode::~CLocationNode( ) { delete [] (PSTR) m_pszLocationId; } CLocationNode* GetNext() { return m_pNext; } CLocationNode* SetNext( CLocationNode* pNext ) { m_pNext = pNext; return m_pNext; } PCSTR GetLocationId() { return m_pszLocationId; } private: PCSTR m_pszLocationId; CLocationNode* m_pNext; };
/////////////////////////////////////////////////////////////////////////////
// CLocationList
class CLocationList { public: CLocationList::CLocationList() { m_iCount = 0; m_pHead = NULL; m_pTail = NULL; } CLocationList::~CLocationList() { Free(); } void CLocationList::Free() { CLocationNode* pNode = m_pHead; for( int i=0; i < m_iCount; i++ ) { CLocationNode* pNodeNext = pNode->GetNext(); delete pNode; pNode = pNodeNext; } m_iCount = 0; m_pHead = NULL; m_pTail = NULL; } CLocationNode* CLocationList::Add( PCSTR pszLocationId ) { CLocationNode* pNode = new CLocationNode( pszLocationId ); if( m_iCount ) m_pTail->SetNext( pNode ); else m_pHead = pNode; m_pTail = pNode; m_iCount++; return pNode; } CLocationNode* CLocationList::Find( PCSTR pszLocationId ) { CLocationNode* pNode = m_pHead; for( int i=0; i < m_iCount; i++ ) { if( strcmp( pszLocationId, pNode->GetLocationId() ) == 0 ) break; CLocationNode* pNodeNext = pNode->GetNext(); pNode = pNodeNext; } return pNode; }
private: int m_iCount; CLocationNode* m_pHead; CLocationNode* m_pTail; };
CLocationList g_LocationSkipList;
/////////////////////////////////////////////////////////////////////////////
// CHHFinder
HRESULT STDMETHODCALLTYPE CHHFinder::FindThisFile(const WCHAR* pwszFileName, WCHAR** ppwszPathName, BOOL* pfRecordPathInRegistry ) { CExCollection* pCollection; CExTitle* pTitle = NULL; PCSTR pszPathName = NULL; CStr PathName; HRESULT hr = S_OK;
// guarantee that we never record this value in the registry since it can always change.
*pfRecordPathInRegistry = FALSE;
CHAR pszFileName[MAX_PATH]; WideCharToMultiByte(CP_ACP, 0, pwszFileName, -1, pszFileName, MAX_PATH, NULL, NULL);
// get a pointer to the title and use this to get the fullpathname
pCollection = GetCurrentCollection(NULL, pszFileName);
if( pCollection ) hr = pCollection->URL2ExTitle( pszFileName, &pTitle );
#if 0
// if this is not a collection or we could not find the title then give
// the ::FindThisFile function a try (since we know removable media
// is not supported for non-collections anyway)
if( !pCollection || !pTitle ) { // check the directory where the master file of the current collection lives
CExCollection* pCurCollection = NULL;
if( g_pCurrentCollection ) pCurCollection = g_pCurrentCollection; else if( g_phmData && g_phmData[0] ) pCurCollection = g_phmData[0]->m_pTitleCollection;
if( pCurCollection ) { CHAR szPathName[_MAX_PATH]; CHAR szFileName[_MAX_FNAME]; CHAR szExtension[_MAX_EXT]; SplitPath((PSTR)pszFileName, NULL, NULL, szFileName, szExtension); CHAR szMasterPath[_MAX_PATH]; CHAR szMasterDrive[_MAX_DRIVE]; SplitPath((PSTR)pCurCollection->m_csFile, szMasterDrive, szMasterPath, NULL, NULL); strcpy( szPathName, szMasterDrive ); CatPath( szPathName, szMasterPath ); CatPath( szPathName, szFileName ); strcat( szPathName, szExtension ); if( (GetFileAttributes(szPathName) != HFILE_ERROR) ) { PathName = szPathName; pszPathName = PathName.psz; } }
if( !pszPathName ) { if( ::FindThisFile( NULL, pszFileName, &PathName, FALSE ) ) { pszPathName = PathName.psz; } else { #ifdef _DEBUG
CHAR szMsg[1024]; wsprintf( szMsg, "HHFinder Debug Message\n\nCould not locate the file \"%s\".", pszFileName ); MsgBox( szMsg, MB_OK ); #endif
return S_OK; } } } #endif
// Removable media support (Refresh bypasses BeforeNavigate so we need this here).
//
// Note, this must be one of the first things we do since the user can
// change the title's location
//
if( pTitle ) { pszPathName = pTitle->GetPathName(); if( FAILED(hr = EnsureStorageAvailability( pTitle )) ) { return S_OK; } }
// if we made it here than this mean we found it (if is does exist)
// and pszPathName points to the full pathname
LPMALLOC pMalloc; WCHAR pwszPathName[MAX_PATH]; *ppwszPathName = NULL; if( pszPathName && *pszPathName ) { MultiByteToWideChar(CP_ACP, 0, pszPathName, -1, pwszPathName, MAX_PATH);
// allocate and copy the pathname
if( SUCCEEDED(hr = CoGetMalloc(1, &pMalloc)) ) { *ppwszPathName = (WCHAR*) pMalloc->Alloc( (wcslen(pwszPathName)+1)*sizeof(WCHAR) ); if( !*ppwszPathName ) { hr = E_OUTOFMEMORY; } else { wcscpy( *ppwszPathName, pwszPathName ); hr = S_OK; } pMalloc->Release(); } }
if (*ppwszPathName == NULL) hr = STG_E_FILENOTFOUND;
return hr; }
/////////////////////////////////////////////////////////////////////////////
// EnsureStorageAvailability
// Code to detect and handle Advanced Media Support issues (formerly RMS issues)
//
// Types are:
//
// HHRMS_TYPE_TITLE (default)
// HHRMS_TYPE_COMBINED_QUERY
// HHRMS_TYPE_ATTACHMENT // a.k.a Sample
//
// return values are as follows:
// S_OK - The storage is available (party on!)
// HHRMS_S_LOCATION_UPDATE - The user changed the location of the volume
// E_FAIL - The storage is unknown (caller should handle this failure condition)
// HHRMS_E_SKIP - User choose to skip this volume just this time
// HHRMS_E_SKIP_ALWAYS - User choose to skip this volume for this entire session
//
// For URL navigation, we should always volume check and always prompt.
//
// For Queries, we should volume check for chm files and not volume check for chq files
// and we will always prompt for the volume for this session unless the user
// selects cancel.
//
HRESULT EnsureStorageAvailability( CExTitle* pTitle, UINT uiFileType, BOOL bVolumeCheckIn, BOOL bAlwaysPrompt, BOOL bNeverPrompt ) { HRESULT hr = S_OK;
// if we do not have a title pointer this indicates that the URL does not belong to a
// compressed title and thus we should claim the storage is available and let IE decide
// what to do with it
if( !pTitle ) return S_OK;
BOOL bVolumeCheck = bVolumeCheckIn;
// Get the location information
LOCATIONHISTORY* pLocationHistory = pTitle->GetUsedLocation();
// Get the collection
CExCollection* pCollection = pTitle->m_pCollection;
// Only check removable media when running in a collection
//
if(pCollection && pCollection->IsSingleTitle()) return S_OK;
// Get the location identifier
CHAR szLocationId[MAX_PATH]; CLocation* pLocation = NULL; if( pLocationHistory ) {
switch( uiFileType ) {
case HHRMS_TYPE_TITLE: strcpy( szLocationId, pLocationHistory->LocationId ); break;
case HHRMS_TYPE_COMBINED_QUERY: if( pLocationHistory->QueryLocation && pLocationHistory->QueryLocation[0] ) strcpy( szLocationId, pLocationHistory->QueryLocation ); else if( pLocationHistory->LocationId && pLocationHistory->LocationId[0] ) strcpy( szLocationId, pLocationHistory->LocationId ); break;
case HHRMS_TYPE_ATTACHMENT: if( pLocationHistory->SampleLocation && pLocationHistory->SampleLocation[0] ) strcpy( szLocationId, pLocationHistory->SampleLocation ); else if( pLocationHistory->LocationId && pLocationHistory->LocationId[0] ) strcpy( szLocationId, pLocationHistory->LocationId ); break;
default: strcpy( szLocationId, pLocationHistory->LocationId ); break;
}
pLocation = pCollection->m_Collection.FindLocation( szLocationId ); }
// if we have location information then get the details about it
// otherwise never prompt or volume check (check existence only).
PCSTR pszVolumeLabel = NULL; PCSTR pszVolumeName = NULL; if( pLocation ) { pszVolumeLabel = pLocation->GetVolume(); // Get the volume label
pszVolumeName = pLocation->GetTitle(); // Get volume's friendly name
} else { bVolumeCheck = FALSE; bNeverPrompt = TRUE; }
// Get the pathname
PCSTR pszPathname = NULL; switch( uiFileType ) {
case HHRMS_TYPE_TITLE: pszPathname = pTitle->GetPathName(); break;
case HHRMS_TYPE_COMBINED_QUERY: pszPathname = pTitle->GetQueryName(); break;
case HHRMS_TYPE_ATTACHMENT: pszPathname = pTitle->GetCurrentAttachmentName(); break;
default: return E_FAIL; break;
}
// Get the location path and filename
CHAR szPath[MAX_PATH]; CHAR szFilename[MAX_PATH]; PCSTR pszPath = szPath; szPath[0]= 0; szFilename[0]= 0; if( pLocation ) { strcpy( szPath, pLocation->GetPath() ); CHAR szExt[MAX_PATH]; CHAR szTmpPath[MAX_PATH]; CHAR szDrive[MAX_PATH]; CHAR szDir[MAX_PATH]; szTmpPath[0] = 0; SplitPath( pszPathname, szDrive, szDir, szFilename, szExt ); strcat( szFilename, szExt ); // make sure that the filename includes and subdirs not part of the path
//
// for example the path may be e:\samples but the pathname is c:\samples\sfl\samp.sfl
// and thus the path is e:\samples but the filename should be sfl\samp.sfl and not
// just samp.sfl
if( szDrive[0] ) strcpy( szTmpPath, szDrive ); if( szDir ) strcat( szTmpPath, szDir ); // STang:
// Buggy, must make sure pszPath is a prefix of szTmpPath ( except the drive letter )
// if( strlen( szTmpPath ) != strlen( pszPath ) )
if( strnicmp(pszPath+1,szTmpPath+1,(int)strlen(pszPath)-1) == 0 && strlen( szTmpPath ) > strlen( pszPath ) ) { CHAR sz[MAX_PATH]; strcpy( sz, &szTmpPath[strlen(pszPath)] ); strcat( sz, szFilename ); strcpy( szFilename, sz ); } } else GetPathAndFileName( pszPathname, szPath, szFilename );
// make sure to disable the default error message the OS displays
// when doing a file check on removable media
UINT uiErrorMode = SetErrorMode( SEM_FAILCRITICALERRORS );
// get the drive of the path
CHAR szDriveRoot[4]; lstrcpyn( szDriveRoot, szPath, 4 ); #define mkupper(c) ((c)-'a'+'A')
if( szDriveRoot[0] >= 'a' ) szDriveRoot[0] = mkupper(szDriveRoot[0]); // make it upper case
// Make copies of various settings to support location updating
CHAR szVolumeLabelTry[MAX_PATH]; CHAR szPathTry[MAX_PATH]; CHAR szPathnameTry[MAX_PATH]; CHAR szDriveRootTry[4];
// setup the paths to try
strcpy( szPathTry, szPath ); strcpy( szPathnameTry, pszPathname ); strcpy( szDriveRootTry, szDriveRoot ); if( bVolumeCheck ) { //HH Bug 2521: Make sure pszVolumeLabel is non-null before copy.
ASSERT( pszVolumeLabel ); strcpy( szVolumeLabelTry, pszVolumeLabel ); } else { strcpy( szVolumeLabelTry, "" ); }
// Setup prompting loop starting conditions
BOOL bExistenceCheck = TRUE; BOOL bPrompt = FALSE;
// === MAIN PROMPTING LOOP BEGINS HERE === //
while( TRUE ) {
// make sure to add a backslash if the second CHAR is a colon
// sometimes we will get just "d:" instead of "d:\" and thus
// GetDriveType will fail under this circumstance
if( szDriveRootTry[1] == ':' ) { szDriveRootTry[2] = '\\'; szDriveRootTry[3] = 0; } // Get media type
UINT uiDriveType = DRIVE_UNKNOWN; if( szDriveRootTry[1] == ':' && szDriveRootTry[2] == '\\' ) { uiDriveType = GetDriveType(szDriveRootTry); } else if( szDriveRootTry[0] == '\\' && szDriveRootTry[1] == '\\' ) { uiDriveType = DRIVE_REMOTE; bVolumeCheck = FALSE; // never check volume label of network drives
}
// Determine and handle the drive types
bExistenceCheck = TRUE; switch( uiDriveType ) {
case DRIVE_FIXED: case DRIVE_RAMDISK: uiDriveType = DRIVE_FIXED; // fall thru
case DRIVE_REMOTE: bVolumeCheck = FALSE; break;
case DRIVE_REMOVABLE: case DRIVE_CDROM: case DRIVE_UNKNOWN: case DRIVE_NO_ROOT_DIR: if( bVolumeCheckIn ) bVolumeCheck = TRUE; break;
default: // unknown types
bVolumeCheck = FALSE; bExistenceCheck = FALSE; break; }
// Prompt for media
if( bPrompt ) { CHAR szDriveLetter[4]; szDriveLetter[0] = szDriveRoot[0]; szDriveLetter[1] = szDriveRoot[1]; szDriveLetter[2] = 0;
HHREMOVABLE Removable; Removable.uiDriveType = uiDriveType; Removable.pszDriveLetter = szDriveLetter; Removable.pszVolumeName = pszVolumeName; PSTR pszPathTry = szPathTry; Removable.ppszLocation = &pszPathTry;
HCURSOR hCursor = GetCursor();
// Disable all of the toplevel application windows, before we bring up the dialog.
CLockOut LockOut ; LockOut.LockOut(GetActiveWindow()) ;
// Display the dialog box.
INT_PTR iReturn = DialogBoxParam( _Module.GetResourceInstance(), MAKEINTRESOURCE(IDD_REMOVEABLE_MEDIA_PROMPT), GetActiveWindow(), RemovableMediaDialogProc, (LPARAM) &Removable );
// Enable all of the windows which we disabled.
LockOut.Unlock() ;
SetCursor( hCursor );
if( iReturn == IDOK ) { strcpy( szPathnameTry, pszPathTry ); CatPath( szPathnameTry, szFilename ); lstrcpyn( szDriveRootTry, pszPathTry, 4 ); bPrompt = FALSE; continue; } else if( iReturn == IDCANCEL ) { if( !bAlwaysPrompt ) g_LocationSkipList.Add( szLocationId ); hr = HHRMS_E_SKIP; break; } }
// Validate media is present using the volume label, if needed
if( bVolumeCheck ) { CHAR szVolume[MAX_PATH]; szVolume[0] = 0; CHAR szFileSystemName[MAX_PATH]; DWORD dwMaximumComponentLength = 0; DWORD dwFileSystemFlags = 0; BOOL bReturn = GetVolumeInformation( szDriveRootTry, szVolume, sizeof(szVolume), NULL, &dwMaximumComponentLength, &dwFileSystemFlags, szFileSystemName, sizeof(szFileSystemName) ); if( bVolumeCheckIn && (!bReturn || (strcmp( szVolume, szVolumeLabelTry ) != 0)) ) bExistenceCheck = FALSE; }
// if the file exists, and it matches the chi file (for title checks only) the we have the right media
if( bExistenceCheck && IsFile( szPathnameTry ) && ((uiFileType==HHRMS_TYPE_TITLE)?pTitle->EnsureChmChiMatch( szPathnameTry ):TRUE ) ) { hr = S_OK;
// TODO: the version of MSDN that shipped with VS 6.0 is broken for net installs.
// For a network install, they erroneously set the volume label for CD2, also
// known as "98VS-1033-CD2", to "DN600ENU1" instead of "DN600ENU2". To fix this we
// need to ignore the language settings of "1033" or "ENU" and make the appropriate
// change to the volume label. We must do this before we call UpdateLocation since
// it could change the location information for CD1 when the user updates the CD2
// location information.
// Never change the volume label unless the new destination is
// removable media!
//
// Setup should adhere to the following rules:
//
// 1. Each local disk and network destination path must use a
// volume name unique for each set of titles from each CD source
// and they must be unique from the CD source volume label.
// It is advised that these volume names be the volume label name
// of the removable media (sahipped media) that the group came
// from appended with the destination type name and number such as
// "-LocalX" or "-NetX".
// 2. Volume names for CD "destinations" must be identical to the
// CD's volume name.
// 3. Note, locations with the same volume name will automatically
// get their path updated when any one of them changes.
//
// if the path did change then update the information, otherwise were done
if( lstrcmpi( szPathTry, szPath ) != 0 ) { // STang
char * pcVolume = NULL; if ( ( (uiDriveType == DRIVE_REMOVABLE) || (uiDriveType == DRIVE_CDROM) ) && bVolumeCheck ) pcVolume = szVolumeLabelTry;
pCollection->UpdateLocation( (PSTR) szLocationId, szPathTry, pcVolume );
// pCollection->UpdateLocation( (PSTR) szLocationId, szPathTry,
// ( (uiDriveType == DRIVE_REMOVABLE) || (uiDriveType == DRIVE_CDROM)) ? szVolumeLabelTry : NULL );
hr = HHRMS_S_LOCATION_UPDATE; }
break; }
// Bail out if we never want to prompt for media
if( bNeverPrompt ) {
#ifdef _DEBUG
if( g_bShowMessage && (uiFileType != HHRMS_TYPE_COMBINED_QUERY) ) { CHAR szMsg[1024]; wsprintf( szMsg, "HHFinder Debug Message\n\n" "Could not find the file:\n \"%s\"\n" "at the location specified.", szPathnameTry ); if( pTitle && pTitle->m_pTitle ) { CHAR szMsg2[1024]; wsprintf( szMsg2, "\n\nTitle ID: \"%s\".", pTitle->m_pTitle->GetId() ); strcat( szMsg, szMsg2 ); } strcat( szMsg, "\n\nPress 'OK' to continue or 'Cancel' to disable this warning."); int iReturn = MsgBox( szMsg, MB_OKCANCEL ); if( iReturn == IDCANCEL ) g_bShowMessage = FALSE; } #endif
// if existence check was desired then this is a failure condition
if( bExistenceCheck ) { hr = E_FAIL; break; }
// Bailout and let the caller know we are skipping this one
hr = HHRMS_E_SKIP; break; }
// If we do not require that we always prompt, check the volume against
// our skip list
if( !bAlwaysPrompt ) { if( !bNeverPrompt ) if( g_LocationSkipList.Find( szLocationId ) ) { hr = HHRMS_E_SKIP_ALWAYS; break; } }
#ifdef _DEBUG
// Let the user know that we could not find the title at the location specified
if( bPrompt ) { CHAR szMsg[1024]; wsprintf( szMsg, "HHFinder Debug Message\n\n" "Could not find the file:\n \"%s\"\n" "at the location specified.", szFilename ); if( pTitle && pTitle->m_pTitle ) { CHAR szMsg2[1024]; wsprintf( szMsg2, "\n\nTitle ID: \"%s\".", pTitle->m_pTitle->GetId() ); strcat( szMsg, szMsg2 ); } MsgBox( szMsg, MB_OKCANCEL ); } #endif
// restore the original path information, and continue
strcpy( szPathTry, szPath ); strcpy( szPathnameTry, pszPathname ); strcpy( szDriveRootTry, szDriveRoot ); if( bVolumeCheck ) { //HH Bug 2521: Make sure pszVolumeLabel is non-null before copy.
ASSERT( pszVolumeLabel ); strcpy( szVolumeLabelTry, pszVolumeLabel ); } else { strcpy( szVolumeLabelTry, "" ); } bPrompt = TRUE; }
// === MAIN PROMPTING LOOP ENDS HERE === //
// restore the previous error mode
SetErrorMode( uiErrorMode );
return hr; }
/////////////////////////////////////////////////////////////////////////////
// CD Swap Dialog
INT_PTR CALLBACK RemovableMediaDialogProc( HWND hDlg, UINT uMsg, WPARAM wParam, LPARAM lParam ) { static HHREMOVABLE* pRemovable = NULL; static HWND hWndIcon = NULL;
switch( uMsg ) {
case WM_INITDIALOG: { pRemovable = (HHREMOVABLE*) lParam;
// get and set our dialog title title
PCSTR pszTitle = GetStringResource( IDS_MSGBOX_TITLE ); SetWindowText( hDlg, pszTitle );
//get media name and icon
PCSTR pszMediaName = NULL; PCSTR pszIcon = NULL; DWORD dwFormatMessage = 0;
if( pRemovable->uiDriveType == DRIVE_REMOVABLE ) { pszIcon = "IconDisk350"; pszMediaName = GetStringResource( IDS_REMOVABLE_MEDIA_DISK ); // "disk"
dwFormatMessage = IDS_REMOVABLE_MEDIA_MESSAGE_FORMAT; } #ifdef HH_VERSION_1_3
else if( pRemovable->uiDriveType == DRIVE_REMOTE ) { pszIcon = "IconRemote"; pszMediaName = GetStringResource( IDS_REMOVABLE_MEDIA_REMOTE ); // "Network location"
dwFormatMessage = IDS_REMOVABLE_MEDIA_MESSAGE_FORMAT2; } else if( pRemovable->uiDriveType == DRIVE_FIXED ) { pszIcon = "IconFixed"; pszMediaName = GetStringResource( IDS_REMOVABLE_MEDIA_FIXED ); // "local disk"
dwFormatMessage = IDS_REMOVABLE_MEDIA_MESSAGE_FORMAT2; } #endif
else /* if( pRemovable->uiDriveType == DRIVE_CDROM ) */ { pszIcon = "IconCDROM"; pszMediaName = GetStringResource( IDS_REMOVABLE_MEDIA_CDROM ); // "CD-ROM disc"
dwFormatMessage = IDS_REMOVABLE_MEDIA_MESSAGE_FORMAT; }
CHAR szMediaName[64]; strcpy( szMediaName, pszMediaName );
// set the icon
hWndIcon = CreateWindow( TEXT( "static" ), pszIcon, WS_CHILD | WS_CLIPSIBLINGS | WS_VISIBLE | SS_ICON, 15, 15, 0, 0, hDlg, NULL, _Module.GetModuleInstance(), NULL );
// get location message format string
PCSTR pszFormat = GetStringResource( dwFormatMessage ); CHAR szFormat[256]; strcpy( szFormat, pszFormat );
// format the location message
DWORD dwArgCount = 3; #ifdef HH_VERSION_1_3
if( dwFormatMessage == IDS_REMOVABLE_MEDIA_MESSAGE_FORMAT2 ) dwArgCount = 2; #endif
DWORD_PTR* pArg = new DWORD_PTR[dwArgCount];
pArg[0] = (DWORD_PTR) szMediaName; pArg[1] = (DWORD_PTR) pRemovable->pszVolumeName; if( dwArgCount == 3 ) pArg[2] = (DWORD_PTR) pRemovable->pszDriveLetter;
CHAR szMessage[1024];
FormatMessage( FORMAT_MESSAGE_FROM_STRING | FORMAT_MESSAGE_ARGUMENT_ARRAY, szFormat, 0, 0, szMessage, sizeof(szMessage), (va_list*) pArg );
delete [] pArg;
// set the location message
#ifdef HH_VERSION_1_3
::SendMessage(GetDlgItem( hDlg, IDC_LOCATION_NAME ), WM_SETFONT, (WPARAM) _Resource.GetUIFont(), FALSE); #else
::SendMessage(GetDlgItem( hDlg, IDC_LOCATION_NAME ), WM_SETFONT, (WPARAM) _Resource.DefaultFont(), FALSE); #endif
SetWindowText( GetDlgItem( hDlg, IDC_LOCATION_NAME ), szMessage );
// set the location path
#ifdef HH_VERSION_1_3
::SendMessage(GetDlgItem( hDlg, IDC_LOCATION_PATH ), WM_SETFONT, (WPARAM) _Resource.GetUIFont(), FALSE); #else
::SendMessage(GetDlgItem( hDlg, IDC_LOCATION_PATH ), WM_SETFONT, (WPARAM) _Resource.DefaultFont(), FALSE); #endif
SetWindowText( GetDlgItem( hDlg, IDC_LOCATION_PATH ), *(pRemovable->ppszLocation) );
// disable the location path for now
//EnableWindow( GetDlgItem( hDlg, IDC_LOCATION_PATH ), FALSE );
// center the dialog
CenterWindow( GetParent( hDlg ), hDlg );
return TRUE; }
case WM_COMMAND: if( LOWORD(wParam) == IDOK || LOWORD(wParam) == IDCANCEL ) { // return the path
GetWindowText( GetDlgItem( hDlg, IDC_LOCATION_PATH ), (PSTR) *(pRemovable->ppszLocation), MAX_PATH ); // make sure the returned path includes a trailing backslash
PSTR* ppsz = pRemovable->ppszLocation; int iLen = (int)strlen(*ppsz); if( (*ppsz)[iLen-1] != '\\' ) { (*ppsz)[iLen] = '\\'; (*ppsz)[iLen+1] = 0; } DestroyWindow( hWndIcon ); pRemovable = NULL; hWndIcon = NULL; EndDialog( hDlg, LOWORD( wParam ) ); } else if( LOWORD(wParam) == ID_BROWSE ) { CStr strPath; if( DlgOpenDirectory( hDlg, &strPath ) ) { SetWindowText( GetDlgItem( hDlg, IDC_LOCATION_PATH ), strPath.psz ); } } break; }
return FALSE; }
|