我在做C#的一些项目。
我需要获得我
项目从的ListView
的窗口,它的手柄我做这样的事情
I'm doing some project on c#.
I need to get i
item from ListView
window, handle of it I got by doing something like this
IntPtr par_hWnd = API.FindWindow(null, "Form1");
IntPtr child1 = API.FindWindowEx(par_hWnd, (IntPtr)0, null, null);
API
是我的静态类,有很多dllimports从user32.dll中
我能够拿到的项目数量在此的ListView:
API
is my static class with lots of dllimports from "user32.dll"
I am able to get count of items in this ListView:
IntPtr count = API.SendMessage(child1, API.LVM_GETITEMCOUNT, 0, 0);
现在我需要得到项目的文本,但结果却莫名其妙地必须放置在 LVITEM
结构,我不知道该怎么称呼 SendMessage函数正确,以及如何实施
LVITEM
。找不到实例C#。任何帮助?
Now i need to get the text of item, but the result somehow must be placed in the LVITEM
Structure, I don't know how to call SendMessage
correctly, and how to implement LVITEM
in c#. Can't find examples for c#. Any help?
这是比人们想象的更困难。为了得到你想要的信息,你必须在相同的进程空间中包含的ListView
控件的应用程序执行$ C $ C。你可以通过在目标进程是大到足以容纳 LVITEM
结构和字符串数据您预计要返回分配的内存块,然后移动的结构,目标进程。 .NET框架使事情变得相当容易一点上我们这里用的 元帅
类。
This is more difficult than one might think. In order to get the information you're looking for, you have to execute the code in the same process space as the application containing the ListView
control. You do that by allocating a block of memory in the target process that is large enough to hold the LVITEM
structure and the string data you expect to be returned, then move that structure to the target process. The .NET Framework makes things quite a bit easier on us here with the Marshal
class.
一旦你采取的考虑,这是声明的 LVITEM
结构和发送的 LVM_GETITEM
消息来控制使用的 SendMessage函数
功能,你嫌。
Once you've taken that into account, it's a simple matter of declaring the LVITEM
structure and sending the LVM_GETITEM
message to the control using the SendMessage
function, as you suspected.
// P/Invoke declarations
private const int LVM_FIRST = 0x1000;
private const int LVM_GETITEMCOUNT = LVM_FIRST + 4;
private const int LVM_GETITEM = LVM_FIRST + 75;
private const int LVIF_TEXT = 0x0001;
[DllImport("user32.dll"), CharSet = CharSet.Auto]
private static extern IntPtr SendMessage(IntPtr hWnd, int Msg, IntPtr wParam,
IntPtr lParam);
[StructLayoutAttribute(LayoutKind.Sequential)]
private struct LVITEM
{
public uint mask;
public int iItem;
public int iSubItem;
public uint state;
public uint stateMask;
public IntPtr pszText;
public int cchTextMax;
public int iImage;
public IntPtr lParam;
}
然后你可以使用它像这样(假设 hListView
是一个有效的句柄的ListView
控制):
And then you would use it like this (assuming hListView
is a valid handle to a ListView
control):
// Declare and populate the LVITEM structure
LVITEM lvi = new LVITEM();
lvi.mask = LVIF_TEXT;
lvi.cchTextMax = 512;
lvi.iItem = 1; // the zero-based index of the ListView item
lvi.iSubItem = 0; // the one-based index of the subitem, or 0 if this
// structure refers to an item rather than a subitem
lvi.pszText = Marshal.AllocHGlobal(512);
// Send the LVM_GETITEM message to fill the LVITEM structure
IntPtr ptrLvi = Marshal.AllocHGlobal(Marshal.SizeOf(lvi));
Marshal.StructureToPtr(lvi, ptrLvi, false);
SendMessage(hListView, LVM_GETITEM, IntPtr.Zero, ptrLvi);
// Extract the text of the specified item
string itemText = Marshal.PtrToStringAuto(lvi.pszText);