none
Applying desktop folder changing

    Question

  • Hi all. I need to dynamically change desktop folder in my C# program) but only solution that I could find to apply such registry changes is killing explorer.exe and waiting while system restart it. But after killing explorer some tray icons disappear, tasks order in taskbar becomes inverted, problems with language switching occurs and so on.
    Tweak UI utility change desktop folder without killing explorer or restarting system, it only need to right click on desktop and refresh it to see result. Does anybody know how to apply desktop folder registry changes like Tweak UI do it, without killing explorer or restarting system?
    Thursday, June 04, 2009 9:12 PM

Answers

  • Resolved. SHChangeNotify with SHCNE_RENAMEFOLDER doing this. Thanks to all. Here is a source.
    1) Define Pinvoke functions:
    [DllImport("shell32.dll")]
    public static extern Int32 SHParseDisplayName( [MarshalAs(UnmanagedType.LPWStr)] String pszName, 
    IntPtr pbc, out IntPtr ppidl, UInt32 sfgaoIn,  out UInt32 psfgaoOut);
    
    [DllImport("Shell32.dll")]
    public static extern int SHChangeNotify(int eventId, int flags, IntPtr item1, IntPtr item2);
    2) Method to notify system about new desktop folder path:
    public static void ApplyNewDesktopPath(string OldDesktop, string NewDesktop)
    {
         uint iAttribute;
         IntPtr oldPidl;
         IntPtr newPidl;
         SHParseDisplayName(OldDesktop, IntPtr.Zero, out oldPidl, 0, out iAttribute);
         SHParseDisplayName(NewDesktop, IntPtr.Zero, out newPidl, 0, out iAttribute);
         SHChangeNotify(0x00020000, 0x1000, oldPidl, newPidl);
    }
    3) Refresh desktop to show new content:
    public static void RefreshDesktop()
    {
        SHChangeNotify(0x8000000, 0x1000, IntPtr.Zero, IntPtr.Zero);
    }

    • Marked as answer by Shoar Friday, June 05, 2009 1:56 PM
    Friday, June 05, 2009 1:56 PM
  • Have you tried calling SHChangeNotify?
    Mattias, C# MVP
    • Marked as answer by Shoar Friday, June 05, 2009 1:56 PM
    Friday, June 05, 2009 7:17 AM

All replies

  • You could do a PostMessage() call to Explorer.  There's a defined msg that will cause it to refresh....but unfortunately, I don't recall the exact value, and a quick Googling didn't turn it up.   You'll have to research this if you want to go with this approach.
    Michael Asher
    Thursday, June 04, 2009 11:01 PM
  • Have you tried calling SHChangeNotify?
    Mattias, C# MVP
    • Marked as answer by Shoar Friday, June 05, 2009 1:56 PM
    Friday, June 05, 2009 7:17 AM
  • Resolved. SHChangeNotify with SHCNE_RENAMEFOLDER doing this. Thanks to all. Here is a source.
    1) Define Pinvoke functions:
    [DllImport("shell32.dll")]
    public static extern Int32 SHParseDisplayName( [MarshalAs(UnmanagedType.LPWStr)] String pszName, 
    IntPtr pbc, out IntPtr ppidl, UInt32 sfgaoIn,  out UInt32 psfgaoOut);
    
    [DllImport("Shell32.dll")]
    public static extern int SHChangeNotify(int eventId, int flags, IntPtr item1, IntPtr item2);
    2) Method to notify system about new desktop folder path:
    public static void ApplyNewDesktopPath(string OldDesktop, string NewDesktop)
    {
         uint iAttribute;
         IntPtr oldPidl;
         IntPtr newPidl;
         SHParseDisplayName(OldDesktop, IntPtr.Zero, out oldPidl, 0, out iAttribute);
         SHParseDisplayName(NewDesktop, IntPtr.Zero, out newPidl, 0, out iAttribute);
         SHChangeNotify(0x00020000, 0x1000, oldPidl, newPidl);
    }
    3) Refresh desktop to show new content:
    public static void RefreshDesktop()
    {
        SHChangeNotify(0x8000000, 0x1000, IntPtr.Zero, IntPtr.Zero);
    }

    • Marked as answer by Shoar Friday, June 05, 2009 1:56 PM
    Friday, June 05, 2009 1:56 PM
  • I am trying to accomplish the same thing. I changed the desktop folder in the registry (shell folders and User shell folders) but I can't get it to refresh (only when I kill and restart explorer).

    I update the registry, call the ApplynewDesktopPath(oldpath, newpath) and call RefreshDesktop.

     

    Can anyone confirm that this works on Win7?

    Thursday, September 02, 2010 2:49 PM
  • This is the code I am using.The registry is updated and I can see the desktop refresh (F5 refresh). Unfortunately the folder does not change. Am I missing something?

     

    ChangeDesktopFolder(@"C:\Users\Anti\Desktop", @"C:\Users\Anti\Desktop\Desktop2");
    
    public void ChangeDesktopFolder(string oldPath, string newPath)
        {
          Registry.SetValue(@"HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\Explorer\Shell Folders", "Desktop",newPath);
          Registry.SetValue(@"HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\Explorer\User Shell Folders", "Desktop",newPath);
    
          uint iAttribute;
          IntPtr oldPidl = IntPtr.Zero;
          IntPtr newPidl = IntPtr.Zero;
          SHParseDisplayName(oldPath, IntPtr.Zero, out oldPidl, 0, out iAttribute);
          SHParseDisplayName(newPath, IntPtr.Zero, out newPidl, 0, out iAttribute);
    
          SHChangeNotify((uint)SHCNE.SHCNE_RENAMEFOLDER, (uint)SHCNF.SHCNF_IDLIST, oldPidl, newPidl);
          SHChangeNotify((uint)SHCNE.SHCNE_INTERRUPT, (uint)SHCNF.SHCNF_FLUSH, IntPtr.Zero, IntPtr.Zero);
        }
    

    Tuesday, September 07, 2010 12:13 PM
  • I see you eventually did find the answer.  It would have saved me a lot of time had you returned to all your earlier questions to provide that solution...

     

    Change Desktop Folder

    • Edited by kijoshua Friday, November 05, 2010 7:38 PM fixed link name
    • Proposed as answer by kijoshua Friday, November 05, 2010 7:38 PM
    Friday, November 05, 2010 7:37 PM