Misc.cpp
上传用户:hy_wanghao
上传日期:2007-01-08
资源大小:279k
文件大小:9k
源码类别:

Shell编程

开发平台:

Visual C++

  1. #include "stdafx.h"
  2. #include "misc.h"
  3. ////////////////////////////////////////////
  4. // PIDL helper functions
  5. // Extracts the complete path from a complex PIDL list.
  6. // The root "/" is prepended to the final path.
  7. void PidlGetFullPath(LPTSTR pstrPath, LPCITEMIDLIST pidl, LPCTSTR cSep/*="/"*/)
  8. {
  9.    ATLASSERT(!::IsBadWritePtr(pstrPath,MAX_PATH));
  10.    ATLASSERT(cSep);
  11.    // Create the full path from the PIDL list
  12.    _tcscpy( pstrPath, cSep );
  13.    while( (pidl!=NULL) && (pidl->mkid.cb!=0) ) {
  14.       ATLASSERT(((LPPIDLDATA)pidl)->tag==PIDL_TAG);
  15.       _tcscat( pstrPath, ((LPPIDLDATA)pidl)->szName );
  16.       pidl = CPidl::_GetNextItem(pidl);
  17.       if( pidl->mkid.cb!=0 ) _tcscat( pstrPath, cSep );
  18.    };
  19. }
  20. // Extracts the path from a complex PIDL list, leaving out
  21. // the last entry (which is assumed to be the filename).
  22. // The root "/" is prepended to the final path.
  23. void PidlGetFilePath(LPTSTR pstrPath, LPCITEMIDLIST pidl, LPCTSTR cSep/*="/"*/)
  24. {
  25.    ATLASSERT(!::IsBadWritePtr(pstrPath,MAX_PATH));
  26.    ATLASSERT(cSep);
  27.    UINT nCount = CPidl::_GetCount(pidl);
  28.    _tcscpy( pstrPath, cSep );
  29.    if( nCount==0 ) return;
  30.    for( UINT i=0; i<nCount-1; i++ ) {
  31.       ATLASSERT(((LPPIDLDATA)pidl)->tag==PIDL_TAG);
  32.       _tcscat( pstrPath, ((LPPIDLDATA)pidl)->szName );
  33.       pidl = CPidl::_GetNextItem(pidl);
  34.       if( pidl->mkid.cb!=0 ) _tcscat( pstrPath, cSep );
  35.    }
  36. }
  37. // Extracts the Name from a complex PIDL list.
  38. void PidlGetName(LPTSTR pstrName, LPCITEMIDLIST pidl)
  39. {
  40.    ATLASSERT(!::IsBadWritePtr(pstrName,MAXNAMELEN));
  41.    pidl = CPidl::_GetLastItem(pidl);
  42.    if( (pidl!=NULL) && (pidl->mkid.cb!=0) ) {
  43.       ATLASSERT(((LPPIDLDATA)pidl)->tag==PIDL_TAG);
  44.       _tcscpy( pstrName, ((LPPIDLDATA)pidl)->szName );
  45.    }
  46.    else {
  47.       pstrName[0] = _T('');
  48.    }
  49. }
  50. // Returns the PIDLTYPE type of the last PIDL entry
  51. PIDLTYPE PidlGetType(LPCITEMIDLIST pidl)
  52. {
  53.    if( pidl==NULL ) return PT_UNKNOWN;
  54.    LPPIDLDATA pData = (LPPIDLDATA)CPidl::_GetLastItem(pidl);
  55.    ATLASSERT(pData->tag==PIDL_TAG);
  56.    return pData->type;
  57. }
  58. ////////////////////////////////////////////
  59. // Misc helper functions
  60. // Open and prepare an Amiga device and volume.
  61. // If a path is supplied (in the 'pidl' argument) the folder will be changed
  62. // right away.
  63. // NOTE:
  64. // Currently this implementation will always get the first partition if more
  65. // than one is found on the device.
  66. HRESULT OpenAmigaDevice(LPCTSTR pstrDevPath, 
  67.                         BOOL bReadOnly, 
  68.                         LPCITEMIDLIST pidlStartFolder, 
  69.                         CAdfDevice &dev, 
  70.                         CAdfVolume &vol)
  71. {
  72.    ATLASSERT(!::IsBadStringPtr(pstrDevPath, MAX_PATH));
  73.    ATLASSERT(!dev.IsOpen());
  74.    ATLASSERT(!vol.IsOpen());
  75.    // Open the Device
  76.    // HACK: If we're started from the MyComputer CLSID, then this is a native Amiga device.
  77.    //       The shell reports a path like "::{CLSID_DRIVES}{CLSID_Drive}".
  78.    //       On WinNT 4.0, ::SHGetPathFromIDList() fails and the string is empty.
  79.    
  80.    // Floppies and hard-files read from this partition.
  81.    // BUG: Hmm! Need to handle multiple partitions
  82.    DWORD nPartition = 0;
  83.    
  84.    // Do we need to initialize the native drive path?
  85.    if( (*pstrDevPath==_T('')) || 
  86.        (_tcsncmp(pstrDevPath, _T("::"), 2)==0) ) {
  87.       static TCHAR s_szDeviceName[MAX_PATH] = { 0 };
  88.       static DWORD s_nPartition = 0;
  89.       if( s_szDeviceName[0]==_T('') ) {
  90.          // Set the default device and partition
  91.          _tcscpy( s_szDeviceName, _T("|H1") );
  92.          s_nPartition = 0;
  93.          // Open registry and find device name and partition
  94.          OLECHAR szCLSID[64];
  95.          ::StringFromGUID2(CLSID_Drive, szCLSID, lengthof(szCLSID));
  96.          TCHAR szSubKey[80];
  97.          LONG lResult;
  98.          ::wsprintf(szSubKey, _T("CLSID\%ls"), szCLSID);
  99.          CRegKey reg;
  100.          lResult = reg.Open(HKEY_CLASSES_ROOT, szSubKey);
  101.          if( lResult==ERROR_SUCCESS ) {
  102.             DWORD dwCount = MAX_PATH;
  103.             reg.QueryValue(s_szDeviceName, _T("DeviceName"), &dwCount);
  104.             reg.QueryValue(s_nPartition, _T("Partition"));
  105.          }
  106.       }
  107.       pstrDevPath = s_szDeviceName;
  108.       nPartition = s_nPartition;
  109.    }
  110.    // Open Amiga device
  111.    if( dev.Open(pstrDevPath)==FALSE ) return E_INVALIDARG;
  112.    if( dev.GetPartitionCount() >= nPartition ) nPartition = 0;
  113.    // Then mount the volume...
  114.    if( dev.Mount(nPartition, bReadOnly, vol)==FALSE ) return E_ACCESSDENIED;
  115.    // If a path is supplied, change folder right away...
  116.    if( pidlStartFolder!=NULL ) {
  117.       TCHAR szPath[MAX_PATH];
  118.       PidlGetFullPath(szPath, pidlStartFolder);
  119.       if( vol.ChangeDirectory(szPath)==FALSE ) return E_FAIL;
  120.    }
  121.    return S_OK;
  122. }
  123. // Initializes our ImageList with default images.
  124. // Because almost all Windows versions have different system icons, we
  125. // need to query for icons like "folder", "binary file"...
  126. BOOL CreateImageLists()
  127. {
  128.    // Set the small image list
  129.    int nSmallCx = ::GetSystemMetrics(SM_CXSMICON);
  130.    int nSmallCy = ::GetSystemMetrics(SM_CYSMICON);
  131.    HIMAGELIST imgSmall = ImageList_Create(nSmallCx, nSmallCy, ILC_COLORDDB | ILC_MASK, 4, 0);
  132.    if( imgSmall==NULL ) return FALSE;
  133.    // Set the large image list
  134.    int nLargeCx = ::GetSystemMetrics(SM_CXICON);
  135.    int nLargeCy = ::GetSystemMetrics(SM_CYICON);
  136.    HIMAGELIST imgLarge = ImageList_Create(nLargeCx, nLargeCy, ILC_COLORDDB | ILC_MASK, 4, 0);
  137.    if( imgLarge==NULL ) return FALSE;
  138.    HICON hIcon;
  139.    SHFILEINFO sfi;
  140.    TCHAR szPath[MAX_PATH];
  141.    // Root icon
  142.    hIcon = (HICON)::LoadImage(_Module.GetResourceInstance(), 
  143.                               MAKEINTRESOURCE(IDI_APP),
  144.                               IMAGE_ICON, 
  145.                               nSmallCx, nSmallCy, 
  146.                               LR_DEFAULTCOLOR);
  147.    ImageList_AddIcon(imgSmall, hIcon);
  148.    hIcon = (HICON)::LoadImage(_Module.GetResourceInstance(), 
  149.                               MAKEINTRESOURCE(IDI_APP),
  150.                               IMAGE_ICON, 
  151.                               nLargeCx, nLargeCy, 
  152.                               LR_DEFAULTCOLOR);
  153.    ImageList_AddIcon(imgLarge, hIcon);
  154.    // Folder icon (get the icon for path "C:Windows")...
  155.    ::GetWindowsDirectory(szPath, lengthof(szPath));
  156.    hIcon = (HICON)::SHGetFileInfo( szPath, 0, &sfi, sizeof(sfi), SHGFI_ICON | SHGFI_SHELLICONSIZE | SHGFI_SMALLICON );
  157.    ImageList_AddIcon(imgSmall, sfi.hIcon);
  158.    hIcon = (HICON)::SHGetFileInfo( szPath, 0, &sfi, sizeof(sfi), SHGFI_ICON | SHGFI_SHELLICONSIZE );
  159.    ImageList_AddIcon(imgLarge, sfi.hIcon);
  160.    // also the open folder icon
  161.    hIcon = (HICON)::SHGetFileInfo( szPath, 0, &sfi, sizeof(sfi), SHGFI_ICON | SHGFI_SHELLICONSIZE | SHGFI_OPENICON | SHGFI_SMALLICON );
  162.    ImageList_AddIcon(imgSmall, sfi.hIcon);
  163.    hIcon = (HICON)::SHGetFileInfo( szPath, 0, &sfi, sizeof(sfi), SHGFI_ICON | SHGFI_SHELLICONSIZE | SHGFI_OPENICON );
  164.    ImageList_AddIcon(imgLarge, sfi.hIcon);
  165.    // File icon (use the icon for this DLL)
  166.    ::GetModuleFileName(_Module.GetModuleInstance(), szPath, lengthof(szPath));
  167.    hIcon = (HICON)::SHGetFileInfo( szPath, 0, &sfi, sizeof(sfi), SHGFI_ICON | SHGFI_SHELLICONSIZE | SHGFI_SMALLICON );
  168.    ImageList_AddIcon(imgSmall, sfi.hIcon);
  169.    hIcon = (HICON)::SHGetFileInfo( szPath, 0, &sfi, sizeof(sfi), SHGFI_ICON | SHGFI_SHELLICONSIZE );
  170.    ImageList_AddIcon(imgLarge, sfi.hIcon);
  171.    _Module.m_ImageLists.m_hImageListSmall = imgSmall;
  172.    _Module.m_ImageLists.m_hImageListLarge = imgLarge;
  173.    return TRUE;
  174. }
  175. ////////////////////////////////////////////
  176. // Debug functions
  177. #ifdef _DEBUG
  178. // A DEBUG function which returns the name of a CLIPFORMAT.
  179. // Windows sends a lot of really weird formats to inform the
  180. // IDataObject about various state changes.
  181. LPTSTR DbgGetCF(CLIPFORMAT cf)
  182. {
  183.    static TCHAR szName[128];
  184.    *szName = _T('');
  185.    ::GetClipboardFormatName(cf, szName, 128);
  186.    return szName;
  187. }
  188. // A DEBUG function which returns the item name of the
  189. // PIDL structure.
  190. // The PIDL must be of PIDLDATA type.
  191. LPTSTR DbgGetPidlPath(LPCITEMIDLIST pidl)
  192. {
  193.    static TCHAR szName[MAX_PATH];
  194.    if( pidl==NULL ) return _T("<null>");
  195.    PidlGetFullPath(szName, pidl);
  196.    return szName;
  197. }
  198. // A DEBUG function which returns the CLSID or interface name
  199. // for the IID argument.
  200. LPTSTR DbgGetIID(REFIID iid)
  201. {
  202.    USES_CONVERSION;
  203.    static TCHAR szName[64];
  204.    OLECHAR szGUID[64];
  205.    ::StringFromGUID2(iid, szGUID, lengthof(szGUID));
  206.    // Attempt to find it in the interfaces section
  207.    CRegKey key;
  208.    DWORD dwType, dw = sizeof(szName);
  209.    key.Open(HKEY_CLASSES_ROOT, _T("Interface"), KEY_READ);
  210.    if( key.Open(key, OLE2T(szGUID), KEY_READ) == S_OK ) {
  211.       *szName = _T('');
  212.       ::RegQueryValueEx(key.m_hKey, NULL, NULL, &dwType, (LPBYTE)szName, &dw);
  213.       return szName;
  214.    }
  215.    // Attempt to find it in the clsid section
  216.    key.Open(HKEY_CLASSES_ROOT, _T("CLSID"), KEY_READ);
  217.    if( key.Open(key, OLE2T(szGUID), KEY_READ) == S_OK ) {
  218.       *szName = _T('');
  219.       ::RegQueryValueEx(key.m_hKey, NULL, NULL, &dwType, (LPBYTE)szName, &dw);
  220.       return szName;
  221.    }
  222.    _tcscpy(szName, OLE2CT(szGUID));
  223.    return szName;
  224. }
  225. #endif