using System; using System.Linq; using Vanara.Extensions; using Vanara.InteropServices; using static Vanara.PInvoke.Shell32; namespace Vanara.PInvoke { /// Extension methods for . public static class KnownFolderIdExt { private const string RegPath = @"HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Explorer\FolderDescriptions\"; private const KNOWN_FOLDER_FLAG stdGetFlags = KNOWN_FOLDER_FLAG.KF_FLAG_DEFAULT_PATH | KNOWN_FOLDER_FLAG.KF_FLAG_NOT_PARENT_RELATIVE | KNOWN_FOLDER_FLAG.KF_FLAG_NO_ALIAS | KNOWN_FOLDER_FLAG.KF_FLAG_DONT_VERIFY; /// Retrieves the full path associated with a . /// The known folder. /// The path. public static string FullPath(this KNOWNFOLDERID id) { SHGetKnownFolderPath(id.Guid(), stdGetFlags, HTOKEN.NULL, out var path); return path; } /// Retrieves the IKnownFolder associated with a . /// The known folder. /// The instance. public static IKnownFolder GetIKnownFolder(this KNOWNFOLDERID id) => new IKnownFolderManager().GetFolder(id.Guid()); /// Retrieves the IShellFolder associated with a . /// The known folder. /// The instance. public static IShellFolder GetIShellFolder(this KNOWNFOLDERID id) { using var desktop = ComReleaserFactory.Create(new ShellDesktop() as IShellFolder); using var pidl = id.PIDL(); return desktop.Item.BindToObject(pidl); } /// Retrieves the IShellItem associated with a . /// The known folder. /// The instance. public static IShellItem GetIShellItem(this KNOWNFOLDERID id) { SHGetKnownFolderItem(id.Guid(), KNOWN_FOLDER_FLAG.KF_FLAG_DEFAULT, HTOKEN.NULL, typeof(IShellItem).GUID, out var ppv).ThrowIfFailed(); return (IShellItem)ppv; } /// Gets a registry property associated with this known folder. /// Return type. /// The known folder. /// Name of the property (value under registry key). /// Retrieved value or default(T) if no value exists. public static T GetRegistryProperty(this KNOWNFOLDERID id, string valueName) => (T)Microsoft.Win32.Registry.GetValue(RegPath + id.Guid().ToString("B"), valueName, default(T)); /// Retrieves the Guid associated with a . /// The known folder. /// The GUID associated with the or if no association exists. public static Guid Guid(this KNOWNFOLDERID id) => AssociateAttribute.GetGuidFromEnum(id); /// Retrieves the associated with the . /// The . /// Matching . public static KNOWNFOLDERID KnownFolderId(this System.Environment.SpecialFolder spFolder) { if (spFolder == Environment.SpecialFolder.Personal) return KNOWNFOLDERID.FOLDERID_Documents; if (spFolder == Environment.SpecialFolder.DesktopDirectory) return KNOWNFOLDERID.FOLDERID_Desktop; foreach (KNOWNFOLDERID val in Enum.GetValues(typeof(KNOWNFOLDERID))) if (val.SpecialFolder() == spFolder) return val; throw new InvalidCastException(@"There is not a Known Folder equivalent to this SpecialFolder."); } /// Retrieves the name associated with a . /// The known folder. /// The name. public static string Name(this KNOWNFOLDERID id) => id.GetIKnownFolder().Name(); /// Retrieves the name associated with a . /// The known folder. /// The name. public static string Name(this IKnownFolder kf) { var fd = kf.GetFolderDefinition(); try { return fd.pszName.ToString(); } finally { FreeKnownFolderDefinitionFields(fd); } } /// Retrieves the PIDL associated with a . /// The known folder. /// The PIDL. public static PIDL PIDL(this KNOWNFOLDERID id) { SHGetKnownFolderIDList(id.Guid(), stdGetFlags, HTOKEN.NULL, out var pidl); return pidl; } /// Retrieves the associated with a if it exists. /// The known folder. /// The if defined, null otherwise. public static Environment.SpecialFolder? SpecialFolder(this KNOWNFOLDERID id) => typeof(KNOWNFOLDERID).GetField(id.ToString()).GetCustomAttributes().Select(a => (Environment.SpecialFolder?)a.Equivalent).FirstOrDefault(); } }