A while back I wrote a program that lets you pick and modify windows. It uses WindowFromPoint()
to get a handle to the window under the mouse cursor and calls GetWindowText()
on that to get the window’s title. This works just fine.
I then added the ability to get the title of columns of a list-control. The problem is that unlike GetColumnWidth()
which returns the width, there is no corresponding function to get the title. Instead, getting the title of the column header requires passing a buffer to GetColumn()
to fill with the title. As such, when I assign the pszText
member of an LVCOLUMN
structure to a pointer to a buffer and pass the struct to GetColumn()
, the other process interprets the pointer as within its own memory space. Obviously this won’t work.
I worked around that by using a method from a CodeProject article. It worked great. However I am still confused about why GetWindowText()
did work.
It is confusing because GetWindowText()
works the same as GetColumn()
; it does not return the window title, it takes a buffer/variable to put the title in.
So why does passing a variable to another process to be filled work in one scenario but not another?
Here is a snippet that gets the window title:
// m_Wnd is a pointer to a window class, pointing to a window in another process
CWnd *m_Wnd=WindowFromPoint(point);
// t is a local variable within this program’s address space
CString t;
// passing a reference to a local variable to another process
m_Wnd->GetWindowText(t); //works correctly!
Here is a corresponding snippet to get the title of a column:
// *lc points to a list-control in another process
int colwidth = lc->GetColumnWidth(col); //works correctly!
// local variables
CString colname = _T("");
LVCOLUMN col;
memset(&col, 0, sizeof(col));
col.mask=LVCF_TEXT;
col.cchTextMax=256;
col.pszText=colname.GetBuffer(256); // passing a pointer to local buffer
BOOL ret=lc.GetColumn(colnum, &col); // buffer is empty
colname.ReleaseBuffer();