我正在尝试使用带有FFI gem的Ruby更改Windows 7桌面中图标的位置。
到目前为止,“Managing Desktop Icons”拥有我想要的大部分内容,但它并不适合我。
该文章一度使用LVA_ALIGNLEFT
,但据我所知,我需要根据“LVM_ARRANGE message”使用LVS_ALIGNLEFT
。
require 'ffi'
module Win32
extend FFI::Library
ffi_lib 'user32'
ffi_convention :stdcall
enum :lvm, [:LVM_GETITEMCOUNT, 4100,
:LVM_ARRANGE, 4118,
:LVM_SETITEMPOSITION, 4111]
enum :parameter, [:GW_CHILD, 5,
:LVS_ALIGNLEFT, 2048 ]
# Uses C Function to find the window handle(HWND) of a window with the specified text, in this case 'ProgMan'
attach_function :findWindow,
:FindWindowA,[ :string, :parameter ], :int
# Gets passed in window's child window
attach_function :getChildWindow,
:GetWindow, [ :int, :parameter], :int
# Sends a message to the passed in window
attach_function :sendMessage,
:SendMessageA, [ :int, :lvm, :parameter, :long], :int
end
# Finds Windows handle for FolderView, SysListView32 which is the icon list
DesktopHandle = Win32.findWindow('ProgMan', 0)
DesktopHandle = Win32.getChildWindow(DesktopHandle, :GW_CHILD)
DesktopHandle = Win32.getChildWindow(DesktopHandle, :GW_CHILD)
# Aligns icons left?
Win32.sendMessage(DesktopHandle, :LVM_ARRANGE, :LVS_ALIGNLEFT, 0)
Win32.sendMessage(DesktopHandle, :LVM_ARRANGE, :LVS_ALIGNLEFT, 0)
应该左对齐图标但不执行任何操作。
我已经使用Win32.sendMessage(DesktopHandle, :LVM_GETITEMCOUNT, 0, 0)
来确保我有正确的句柄,这确实输出了相同数量的图标。
我从“LVM_* defs”中获取了大部分值。
我只是不确定为什么这不起作用。
编辑: 看起来左对齐实际上工作我只是没有意识到它在做什么,我认为使用此命令应该已将我的所有图标移动到我的屏幕的左侧,但是此命令仅更改对齐! I.E.在Microsoft单词中,当您左对齐某些内容时,或居中的内容会改变文本的方式。
现在我需要获得改变图标位置的实际部分:
for (int i=0; i<200; i++)
SendMessage(DesktopHandle, LVM_SETITEMPOSITION, 0, MAKELPARAM(10, i));
我仍在寻找的唯一部分是如何在ruby中执行MAKELPARAM(10, I)
部分,我想我可能想要使用Ruby的数组#pack,但我不肯定如何去做
更新: 事实证明我的LVM值的来源不是我需要的,而是我使用了“List-View Messages”中的值。(我更新了我的数字以便以上是好的)
我还为MAKELPARAM()找到了“Ruby Class: Object”。
def MAKELPARAM(w1,w2)
return (w2<<16) | w1
end
这会移动我的一个图标Win32.sendMessage(DesktopHandle, :LVM_SETITEMPOSITION, 0, makeLPARAM(10, 1))
答案 0 :(得分:1)
原来我在sendmessage中发送了错误的值。
计算图标数量的代码,然后将一个图标移动到某个x,y位置(这会将列表中的第一个图标移动到左上角位置,在我的情况下,我当场没有任何内容。
require 'ffi'
module Win32
extend FFI::Library
ffi_lib 'user32'
ffi_convention :stdcall
enum :lvm, [:LVM_GETITEMCOUNT, 4100,
:LVM_DELETEALLITEMS, 4105,
:LVM_GETNEXTITEM, 4108,
:LVM_SETITEMPOSITION, 4111,
:LVM_GETITEMPOSITION, 4112,
:LVM_ARRANGE, 4118,
:LVM_UPDATE, 4138,
:LVM_GETITEMTEXTA, 4141,
:LVM_SETITEMTEXTA, 4142 ]
enum :parameter, [:GW_CHILD, 5,
:LVS_ALIGNLEFT, 2048 ]
# Uses C Function to find the window handle(HWND) of a window with the specified text, in this case 'ProgMan'
attach_function :findWindow,
:FindWindowA,[ :string, :parameter ], :int
# Gets passed in window handle's child window
attach_function :getChildWindow,
:GetWindow, [ :ulong, :parameter], :int
# Sends a message to the passed in window
attach_function :sendMessage,
:SendMessageA, [ :ulong, :lvm, :parameter, :long], :int
end # end of Win32
def makeLPARAM(w1, w2)
return (w2<<16) | w1
end
# Finds Windows handle for FolderView, SysListView32 which is the icon list
DesktopHandle = Win32.findWindow('ProgMan', 0)
DesktopHandle = Win32.getChildWindow(DesktopHandle, :GW_CHILD)
DesktopHandle = Win32.getChildWindow(DesktopHandle, :GW_CHILD)
# Gets count of icons on desktop
Win32.sendMessage(DesktopHandle, :LVM_GETITEMCOUNT, 0, 0)
# Moves the first icon in the list to the top leftmost position on the screen
Win32.sendMessage(DesktopHandle, :LVM_SETITEMPOSITION, 0, makeLPARAM(10, 1))
这比我想象的要困难得多!虽然很多人没有正确的价值观,但是有人能指出一个我应该首先寻找价值观的地方吗?