0

I am working on returning the exact path of the current Active Directory which user has focused on then I found some code, although none of them seems to work correctly and have bugs. But this code seems to work... anyway I want to return the mentioned path (which is called currDirectory in this code; when I change the void type to string type in this code and use return currDirectory, I get an error

Return from an anonymous function converted to a void returning delegate cannot return a value

Can anyone change this code so that it can return the currDirectory as a string?

class Class2
{
    public static void Main()
    {
        RefreshWindow();  
    }

    public static string RefreshWindow()
    {
        Guid CLSID_ShellApplication = new Guid("13709620-C279-11CE-A49E-444553540000");
        Type shellApplicationType = Type.GetTypeFromCLSID(CLSID_ShellApplication, true);

        object shellApplication = Activator.CreateInstance(shellApplicationType);
        object windows = shellApplicationType.InvokeMember("Windows", System.Reflection.BindingFlags.InvokeMethod, null, shellApplication, new object[] { });

        Type windowsType = windows.GetType();
        object count = windowsType.InvokeMember("Count", System.Reflection.BindingFlags.GetProperty, null, windows, null);

        Parallel.For(0, (int)count, i =>
        {
            object item = windowsType.InvokeMember("Item", System.Reflection.BindingFlags.InvokeMethod, null, windows, new object[] { i });
            Type itemType = item.GetType();
            string itemName = (string)itemType.InvokeMember("Name", System.Reflection.BindingFlags.GetProperty, null, item, null);

            if (itemName == "Windows Explorer" || itemName == "File Explorer")
            {
                string currDirectory = HttpUtility.HtmlEncode((string)itemType.InvokeMember("LocationURL", System.Reflection.BindingFlags.GetProperty, null, item, null)).Replace("///", @"\").Replace("/", @"\").Replace("%20", " ").Replace(@"file:\", "");

                Console.WriteLine(currDirectory);
                Console.Read();

                return currDirectory;
            }
        });
    }
}
marc_s
  • 732,580
  • 175
  • 1,330
  • 1,459
M.shahbazi
  • 11
  • 6
  • This is because you are returning inside of the anonymous method you use in your `Parallel.For(0, (int)count, i =>` – AhmedBinGamal Jan 13 '19 at 20:34
  • 1
    It is returning from the lambda expression, not from the `RefreshWindow` method. And since the `Parallel.For` gets several `currDirectory` values in parallel, which one of them do you want to return? See [this answer](https://stackoverflow.com/a/8001776/880990) from [Parallel.ForEach with adding to list](https://stackoverflow.com/questions/8001748/parallel-foreach-with-adding-to-list). – Olivier Jacot-Descombes Jan 13 '19 at 20:40
  • can you change this code so that it returns the currdirectory as a string...i am not famiiar with this. – M.shahbazi Jan 13 '19 at 20:43
  • @M.shahbazi check my answer below. – AhmedBinGamal Jan 13 '19 at 20:48

1 Answers1

1

Your code will not return a single path, it will return all of the opened Windows Explorer instances, so if you opened more than one, all will be returned, Anyway look at my solution below, it should fix your problem.

public static string[] RefreshWindow()
{

    Guid CLSID_ShellApplication = new Guid("13709620-C279-11CE-A49E-444553540000");
    Type shellApplicationType = Type.GetTypeFromCLSID(CLSID_ShellApplication, true);

    object shellApplication = Activator.CreateInstance(shellApplicationType);
    object windows = shellApplicationType.InvokeMember("Windows", System.Reflection.BindingFlags.InvokeMethod, null, shellApplication, new object[] { });

    Type windowsType = windows.GetType();
    var count = (int)windowsType.InvokeMember("Count", System.Reflection.BindingFlags.GetProperty, null, windows, null);

    string[] currentDirectories = new string[count];
    Parallel.For(0, count, i =>
    {
        object item = windowsType.InvokeMember("Item", System.Reflection.BindingFlags.InvokeMethod, null, windows, new object[] { i });
        Type itemType = item.GetType();
        string itemName = (string)itemType.InvokeMember("Name", System.Reflection.BindingFlags.GetProperty, null, item, null);
        if (itemName == "Windows Explorer" || itemName == "File Explorer")
        {
            string currDirectory = HttpUtility.HtmlEncode((string)itemType.InvokeMember("LocationURL", System.Reflection.BindingFlags.GetProperty, null, item, null)).Replace("///", @"\").Replace("/", @"\").Replace("%20", " ").Replace(@"file:\", "");

            currentDirectories[i] =  currDirectory;
        }

    });
    return currentDirectories;
}

Result should be something like that: enter image description here

  • i appreciate your favor.is this code return the current active window which user is focusing on right know? – M.shahbazi Jan 13 '19 at 20:55
  • oooh i know it returns all active one.how can i get path of active current window from this code? – M.shahbazi Jan 13 '19 at 20:59
  • This code "Your original posted code with the void error fixed" returns a list of the opened windows(s) regardless of it being focused. – AhmedBinGamal Jan 13 '19 at 21:00
  • @M.shahbazi please refer to this https://stackoverflow.com/questions/115868/how-do-i-get-the-title-of-the-current-active-window-using-c – AhmedBinGamal Jan 13 '19 at 21:02
  • Also I would appreciate if you would accept and up-vote my answer if it answered your original question :) – AhmedBinGamal Jan 13 '19 at 21:03