📄 itemidlist.h
字号:
CComPtr<IEnumIDList> spEnum;
HRESULT hr = pFolder->EnumObjects(NULL, grfFlags, &spEnum);
if (FAILED(hr))
return __f;
LPITEMIDLIST pidl;
ULONG celtFetched;
while (spEnum->Next(1, &pidl, &celtFetched) == S_OK) {
ATLASSERT(pidl != NULL);
CItemIDList idl; idl.Attach(pidl);
__f(pFolder, idl);
}
return __f;
}
template <typename _Function>
_Function MtlForEachFolderAndFile(IShellFolder* pFolder, _Function __f, bool bIncludeHidden = false)
{
DWORD grfFlags = bIncludeHidden ? SHCONTF_NONFOLDERS|SHCONTF_FOLDERS|SHCONTF_INCLUDEHIDDEN : SHCONTF_NONFOLDERS|SHCONTF_FOLDERS;
CComPtr<IEnumIDList> spEnum;
HRESULT hr = pFolder->EnumObjects(NULL, grfFlags, &spEnum);
if (FAILED(hr))
return __f;
LPITEMIDLIST pidl;
ULONG celtFetched;
while (spEnum->Next(1, &pidl, &celtFetched) == S_OK) {
_INCREMENT_COUNT();
ATLASSERT(pidl != NULL);
CItemIDList idl; idl.Attach(pidl);
__f(pFolder, idl);
}
return __f;
}
*/
template <class _Function>
_Function MtlForEachObject(const CItemIDList& idlFolder, _Function __f, bool bIncludeHidden = false)
{
// get desktop
CComPtr<IShellFolder> spDesktopFolder;
HRESULT hr = ::SHGetDesktopFolder(&spDesktopFolder);
if (FAILED(hr))
return __f;
// get the folder
CComPtr<IShellFolder> spFolder;
hr = spDesktopFolder->BindToObject(idlFolder, NULL, IID_IShellFolder, (void**)&spFolder);
if (FAILED(hr)) {
CItemIDList idl;
hr = ::SHGetSpecialFolderLocation(NULL, CSIDL_DESKTOP, &idl);
if (FAILED(hr))
return __f;
if (idl == idlFolder)// check if same idl or not
spFolder = spDesktopFolder;
else
return __f;
}
DWORD grfFlags = SHCONTF_FOLDERS|SHCONTF_NONFOLDERS;
if (bIncludeHidden)
grfFlags |= SHCONTF_INCLUDEHIDDEN;
CComPtr<IEnumIDList> spEnum;
hr = spFolder->EnumObjects(NULL, grfFlags, &spEnum);
if (FAILED(hr))
return __f;
LPITEMIDLIST pidl;
ULONG celtFetched;
while (spEnum->Next(1, &pidl, &celtFetched) == S_OK) {
_INCREMENT_COUNT();
ATLASSERT(pidl != NULL);
CItemIDList idlFile; idlFile.Attach(pidl);
ULONG dwAttributes = SFGAO_FOLDER;
LPCITEMIDLIST pidls[] = { idlFile.m_pidl };
HRESULT hr = spFolder->GetAttributesOf(1, pidls, &dwAttributes);
if (FAILED(hr))
continue;
bool bFolder = _check_flag(SFGAO_FOLDER, dwAttributes);// check
__f(spFolder, idlFolder, idlFile, bFolder);
}
return __f;
}
template <class _Function>
_Function MtlForEachFolder(const CItemIDList& idlFolder, _Function __f, bool bIncludeHidden = false)
{
// get desktop
CComPtr<IShellFolder> spDesktopFolder;
HRESULT hr = ::SHGetDesktopFolder(&spDesktopFolder);
if (FAILED(hr))
return __f;
// get the folder
CComPtr<IShellFolder> spFolder;
hr = spDesktopFolder->BindToObject(idlFolder, NULL, IID_IShellFolder, (void**)&spFolder);
if (FAILED(hr))
return __f;
DWORD grfFlags = bIncludeHidden ? SHCONTF_FOLDERS|SHCONTF_INCLUDEHIDDEN : SHCONTF_FOLDERS;
CComPtr<IEnumIDList> spEnum;
hr = spFolder->EnumObjects(NULL, grfFlags, &spEnum);
if (FAILED(hr))
return __f;
LPITEMIDLIST pidl;
ULONG celtFetched;
while (spEnum->Next(1, &pidl, &celtFetched) == S_OK) {
_INCREMENT_COUNT();
ATLASSERT(pidl != NULL);
CItemIDList idlFile; idlFile.Attach(pidl);
ULONG dwAttributes = SFGAO_FOLDER;
LPCITEMIDLIST pidls[] = { idlFile.m_pidl };
spFolder->GetAttributesOf(1, pidls, &dwAttributes);
if (dwAttributes & SFGAO_FOLDER) // required
__f(spFolder, idlFolder, idlFile);
}
return __f;
}
template <class _Function>
_Function MtlForEachFile(const CItemIDList& idlFolder, _Function __f, bool bIncludeHidden = false)
{
// get desktop
CComPtr<IShellFolder> spDesktopFolder;
HRESULT hr = ::SHGetDesktopFolder(&spDesktopFolder);
if (FAILED(hr))
return __f;
// get the folder
CComPtr<IShellFolder> spFolder;
hr = spDesktopFolder->BindToObject(idlFolder, NULL, IID_IShellFolder, (void**)&spFolder);
if (FAILED(hr))
return __f;
DWORD grfFlags = bIncludeHidden ? SHCONTF_NONFOLDERS|SHCONTF_INCLUDEHIDDEN : SHCONTF_NONFOLDERS;
CComPtr<IEnumIDList> spEnum;
hr = spFolder->EnumObjects(NULL, grfFlags, &spEnum);
if (FAILED(hr))
return __f;
LPITEMIDLIST pidl;
ULONG celtFetched;
while (spEnum->Next(1, &pidl, &celtFetched) == S_OK) {
_INCREMENT_COUNT();
ATLASSERT(pidl != NULL);
CItemIDList idlFile; idlFile.Attach(pidl);
ULONG dwAttributes = SFGAO_FOLDER;
LPCITEMIDLIST pidls[] = { idlFile.m_pidl };
spFolder->GetAttributesOf(1, pidls, &dwAttributes);
if (!(dwAttributes & SFGAO_FOLDER)) // required
__f(spFolder, idlFolder, idlFile);
}
return __f;
}
inline bool MtlGetDisplayName(IShellFolder* pFolder, LPCITEMIDLIST lpi,
CString& rString, DWORD uFlags = SHGDN_NORMAL)
{
ATLASSERT(pFolder != NULL);
ATLASSERT(lpi != NULL);
STRRET str;
HRESULT hr = pFolder->GetDisplayNameOf(lpi, uFlags, &str);
if (FAILED(hr))
return false;
USES_CONVERSION;
switch (str.uType) {
case STRRET_WSTR:
rString = W2T(str.pOleStr);
break;
case STRRET_OFFSET:
rString = (LPSTR)lpi + str.uOffset;
break;
case STRRET_CSTR:
rString = (LPSTR)str.cStr;
break;
default:
return false;
}
return true;
}
/*
inline CString MtlGetDisplayName(const CString& strFullPath)
{
CComPtr<IShellFolder> spDesktop;
HRESULT hr = ::SHGetDesktopFolder(&spDesktop);
if (FAILED(hr))
return CString();
CString strName;
if (!MtlGetDisplayName(spDesktop, CItemIDList(strFullPath), strName))
return CString();
return strName;
}
*/
inline CString MtlGetDisplayName(LPCITEMIDLIST pidlRelative)
{// The desktop folder can give a name to you even if a relative idl
if (pidlRelative == NULL)
return CString();
CComPtr<IShellFolder> spDesktop;
HRESULT hr = ::SHGetDesktopFolder(&spDesktop);
if (FAILED(hr))
return CString();
CString strName;
if (!MtlGetDisplayName(spDesktop, pidlRelative, strName))
return CString();
return strName;
}
inline CItemIDList MtlSetDisplayName(IShellFolder* pFolder, LPCITEMIDLIST pidl,
LPCTSTR lpszName, HWND hWnd, DWORD uFlags = SHGDN_NORMAL)
{
CItemIDList idl;
USES_CONVERSION;
HRESULT hr = pFolder->SetNameOf(hWnd, pidl, T2COLE(lpszName), uFlags, &idl);
if (SUCCEEDED(hr))
return idl;
return idl;
}
/*
inline bool MtlGetDisplayName(CString& strName, const CString& strFolder, const CString& strObject)
{
CItemIDList idlFolder = strFolder;
CItemIDList idl = strObject;
idl -= idlFolder;
if (idl.IsNull())
return false;
CComPtr<IShellFolder> spDesktop;
HRESULT hr = ::SHGetDesktopFolder(&spDesktop);
if (FAILED(hr))
return false;
CComPtr<IShellFolder> spFolder;
HRESULT hr = spDesktopFolder->BindToObject(idlFolder, NULL, IID_IShellFolder, (void**)&spFolder);
if (FAILED(hr))
return false;
return MtlGetDisplayName(spFolder, idl, strName);
}
*/
bool MtlGetShellFolder(LPCITEMIDLIST pidl, IShellFolder** ppFolder)
{
ATLASSERT(pidl != NULL);
CComPtr<IShellFolder> spDesktop;
HRESULT hr = ::SHGetDesktopFolder(&spDesktop);
if (FAILED(hr))
return false;
hr = spDesktop->BindToObject(pidl, NULL, IID_IShellFolder, (void**)ppFolder);
if (FAILED(hr))
return false;
return true;
}
// Note. It would fail if not the ordinary path.
inline CItemIDList MtlGetFullItemIDList(IShellFolder* pFolder, LPCITEMIDLIST lpi)
{
CString strName;
if (!MtlGetDisplayName(pFolder, lpi, strName, SHGDN_FORPARSING))
return CItemIDList();
CComPtr<IShellFolder> spDesktopFolder;
HRESULT hr = ::SHGetDesktopFolder(&spDesktopFolder);
if (FAILED(hr))
return CItemIDList();
ULONG chEaten;
CItemIDList idlFolder;
USES_CONVERSION;
hr = spDesktopFolder->ParseDisplayName(NULL, NULL, T2OLE((LPTSTR)(LPCTSTR)strName),
&chEaten, &idlFolder, NULL);
if (FAILED(hr))
return CItemIDList();
return idlFolder;
}
inline int MtlGetSystemIconIndex(LPCITEMIDLIST lpi, UINT uFlags = SHGFI_SMALLICON)
{
ATLASSERT(lpi != NULL);
uFlags |= SHGFI_PIDL | SHGFI_SYSICONINDEX;
SHFILEINFO sfi;
DWORD dwResult = ::SHGetFileInfo((LPCTSTR)lpi, 0, &sfi, sizeof(SHFILEINFO), uFlags);
if (dwResult == 0)
return -1;
return sfi.iIcon;
}
inline bool MtlGetAttributesOf(LPCITEMIDLIST pidlFull, ULONG& dwAttributes)
{
CComPtr<IShellFolder> spDesktopFolder;
HRESULT hr = ::SHGetDesktopFolder(&spDesktopFolder);
if (FAILED(hr))
return false;
LPCITEMIDLIST pidls[] = { pidlFull };
hr = spDesktopFolder->GetAttributesOf(1, pidls, &dwAttributes);
if (FAILED(hr))
return false;
return true;
}
// Note. It is possible to make browsing slow.
inline bool MtlHasSubObject(const CItemIDList& idlFolder, bool bIncludeHidden = false)
{
ATLASSERT(idlFolder.m_pidl != NULL);
// get desktop
CComPtr<IShellFolder> spDesktopFolder;
HRESULT hr = ::SHGetDesktopFolder(&spDesktopFolder);
if (FAILED(hr))
return false;
// get the folder
CComPtr<IShellFolder> spFolder;
hr = spDesktopFolder->BindToObject(idlFolder, NULL, IID_IShellFolder, (void**)&spFolder);
if (FAILED(hr))
return false;
DWORD grfFlags = bIncludeHidden ? SHCONTF_FOLDERS|SHCONTF_NONFOLDERS|SHCONTF_INCLUDEHIDDEN : SHCONTF_FOLDERS|SHCONTF_NONFOLDERS;
CComPtr<IEnumIDList> spEnum;
hr = spFolder->EnumObjects(NULL, grfFlags, &spEnum);
if (FAILED(hr))
return false;
LPITEMIDLIST pidl;
ULONG celtFetched;
while (spEnum->Next(1, &pidl, &celtFetched) == S_OK) {
ATLASSERT(pidl != NULL);
CItemIDList idl; idl.Attach(pidl);
return true;
}
return false;
}
// Note. this is still not precise.
inline bool MtlIsRealFolder(const CItemIDList& idlFolder)
{
ATLASSERT(idlFolder.m_pidl != NULL);
// get desktop
CComPtr<IShellFolder> spDesktopFolder;
HRESULT hr = ::SHGetDesktopFolder(&spDesktopFolder);
if (FAILED(hr))
return false;
ULONG dwAttributes = SFGAO_FOLDER;
LPCITEMIDLIST pidls[] = { idlFolder.m_pidl };
hr = spDesktopFolder->GetAttributesOf(1, pidls, &dwAttributes);
if (dwAttributes & SFGAO_FOLDER)
return true;
else
return false;
}
bool MtlShellExecute(HWND hWnd, LPCITEMIDLIST pidl)
{
ATLASSERT(pidl != NULL);
SHELLEXECUTEINFO sei = {
sizeof(SHELLEXECUTEINFO), SEE_MASK_INVOKEIDLIST,
hWnd,
_T(""), _T(""), _T(""), _T(""),
SW_SHOWNORMAL, _Module.GetModuleInstance(),
(LPVOID)pidl,
NULL, 0, 0, NULL
};
return ShellExecuteEx(&sei) == TRUE;
}
inline bool MtlIsTooSlowIDList(LPCITEMIDLIST pidl)
{
TCHAR szPath[MAX_PATH]; szPath[0] = _T('\0');
::SHGetPathFromIDList(pidl, szPath);
CString strExt = CString(szPath).Right(4);
return (strExt.CompareNoCase(_T(".url")) == 0);
}
/*
template <typename _OutputIter>
bool MtlEnumFile(IShellFolder* pFolder, _OutputIter __result, bool bIncludeHidden = false)
{
*__result = *__first;
while (++__first != __last)
if (!(*__result == *__first))
*++__result = *__first;
return ++__result;
DWORD grfFlags = bIncludeHidden ? SHCONTF_NONFOLDERS|SHCONTF_INCLUDEHIDDEN : SHCONTF_NONFOLDERS;
CComPtr<IEnumIDList> spEnum;
HRESULT hr = pFolder->EnumObjects(NULL, grfFlags, &spEnum);
if (FAILED(hr))
return __f;
typedef enum_iterator<IEnumIDList, &IID_IEnumIDList, LPITEMIDLIST> pidl_itor;
for (pidl_itor it = pidl_itor(spEnum, 64); it != pidl_itor(); ++it) {
CItemIDList idl; idl.Attach(*it);
__f(pFolder, idl);
}
return __f;
}
*/
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -