views:

36

answers:

1

In .Net we can retreive the paths to 'special folders', like Documents/Desktop etc. Today I tried to find a way to get the path to the 'Downloads' folder, but it's not special enough it seems.

I know I can just do 'C:\Users\Username\Downloads', but that seems an ugly solution. So how can I retreive the path using .Net?

+2  A: 

Yes it is special, discovering the name of this folder didn't become possible until Vista. .NET still needs to support prior operating systems. The solution isn't pretty but this should work reliably enough:

using System.Runtime.InteropServices;
using System.IO;
...

        public static string GetDownloadsPath() {
            string path = null;
            if (Environment.OSVersion.Version.Major >= 6) {
                IntPtr pathPtr;
                int hr = SHGetKnownFolderPath(ref FolderDownloads, 0, IntPtr.Zero, out pathPtr);
                if (hr == 0) {
                    path = Marshal.PtrToStringUni(pathPtr);
                    Marshal.FreeCoTaskMem(pathPtr);
                    return path;
                }
            }
            path = Path.GetDirectoryName(Environment.GetFolderPath(Environment.SpecialFolder.Personal));
            path = Path.Combine(path, "Downloads");
            return path;
        }

        private static Guid FolderDownloads = new Guid("374DE290-123F-4565-9164-39C4925E467B");
        [DllImport("shell32.dll", CharSet = CharSet.Auto)]
        private static extern int SHGetKnownFolderPath(ref Guid id, int flags, IntPtr token, out IntPtr path);

Feel free to tweak the fallback version, I'm not so sure how accurate it is. Hopefully you'll never need it.

Hans Passant