无法在桌面上切换“将图标对齐网格”

时间:2017-05-08 17:40:46

标签: c# winapi interop

这是我正在使用的代码:

private void Button_Click(object sender, RoutedEventArgs e) {
    SendMessage(GetDesktopWindow(), LVM_ARRANGE, LVA_SNAPTOGRID, 0);
}

public const uint LVM_ARRANGE = 0x1000 + 22;
public const int LVA_SNAPTOGRID = 0x0005;

[DllImport("User32.dll", CharSet = CharSet.Auto)]
public static extern IntPtr GetDesktopWindow();

[DllImport("user32.dll")]
public static extern int SendMessage(IntPtr hWnd, uint msg, int wParam, int lParam);

运行时没有任何反应。代码来自https://www.codeproject.com/Messages/1168961/Re-Auto-Arrange-desktop-icons.aspx

尝试了不同的Windows版本。

1 个答案:

答案 0 :(得分:0)

这段代码对我有用。请注意,它似乎不会更改选项,因此虽然它为我安排了网格,但仍然未选中View-> Align Icons To Grid。这里概述了这个问题:How do I get the window handle of the desktop?

  

你的问题是由一个相当普遍的混淆造成的   桌面窗口实际上是。 GetDesktopWindow函数可以   正是它所记录的内容:它返回一个句柄   桌面窗口。但是,这与包含的窗口不同   桌面图标。

所以我在这里使用了答案:Get handle to desktop / shell window但是更换或添加方法和p / invoke调用,直到我拥有所有必要的东西,因为该链接只提供方法调用而不是dll导入(我可能留下了一些多余的东西在这里。)

static void Main()
{
    SendMessage(GetDesktopWindow(DesktopWindow.SysListView32), LVM_ARRANGE, LVA_SNAPTOGRID, 0);
    Console.ReadLine();
}

public const int LVM_ARRANGE = 4118;
public const int LVA_SNAPTOGRID = 5;

[DllImport("user32.dll")]
static extern IntPtr GetShellWindow();

[DllImport("user32.dll", CharSet = CharSet.Unicode)]
static extern IntPtr FindWindowEx(IntPtr parentHandle, IntPtr childAfter, string lclassName, string windowTitle);

[DllImport("User32.dll", CharSet = CharSet.Auto)]
public static extern IntPtr GetDesktopWindow();

[DllImport("user32.dll")]
public static extern int SendMessage(IntPtr hWnd, uint msg, int wParam, int lParam);

[DllImport("user32.dll")]
private static extern bool EnumWindows(EnumWindowsProc enumProc, IntPtr lParam);
public delegate bool EnumWindowsProc(IntPtr hWnd, IntPtr lParam);


[DllImport("user32.dll", CharSet = CharSet.Unicode)]
private static extern int GetWindowText(IntPtr hWnd, StringBuilder strText, int maxCount);

[DllImport("user32.dll", CharSet = CharSet.Unicode)]
private static extern int GetWindowTextLength(IntPtr hWnd);

public enum DesktopWindow
{
    ProgMan,
    SHELLDLL_DefViewParent,
    SHELLDLL_DefView,
    SysListView32
}

public static IntPtr GetDesktopWindow(DesktopWindow desktopWindow)
{
    IntPtr _ProgMan = GetShellWindow();
    IntPtr _SHELLDLL_DefViewParent = _ProgMan;
    IntPtr _SHELLDLL_DefView = FindWindowEx(_ProgMan, IntPtr.Zero, "SHELLDLL_DefView", null);
    IntPtr _SysListView32 = FindWindowEx(_SHELLDLL_DefView, IntPtr.Zero, "SysListView32", "FolderView");

    if (_SHELLDLL_DefView == IntPtr.Zero)
    {
        EnumWindows((hwnd, lParam) =>
        {
            if (GetWindowText(hwnd) == "WorkerW")
            {
                IntPtr child = FindWindowEx(hwnd, IntPtr.Zero, "SHELLDLL_DefView", null);
                if (child != IntPtr.Zero)
                {
                    _SHELLDLL_DefViewParent = hwnd;
                    _SHELLDLL_DefView = child;
                    _SysListView32 = FindWindowEx(child, IntPtr.Zero, "SysListView32", "FolderView"); ;
                    return false;
                }
            }
            return true;
        }, IntPtr.Zero);
    }

    switch (desktopWindow)
    {
        case DesktopWindow.ProgMan:
            return _ProgMan;
        case DesktopWindow.SHELLDLL_DefViewParent:
            return _SHELLDLL_DefViewParent;
        case DesktopWindow.SHELLDLL_DefView:
            return _SHELLDLL_DefView;
        case DesktopWindow.SysListView32:
            return _SysListView32;
        default:
            return IntPtr.Zero;
    }
}

public static string GetWindowText(IntPtr hWnd)
{
    int size = GetWindowTextLength(hWnd);
    if (size > 0)
    {
        var builder = new StringBuilder(size + 1);
        GetWindowText(hWnd, builder, builder.Capacity);
        return builder.ToString();
    }

    return String.Empty;
}