[SOLVED] How to get notified when mouse moved from one header item to another item

Windows specific questions.
Post Reply
kcvinu
Posts: 232
Joined: Oct 07, 2015 16:44
Location: Keralam, India

[SOLVED] How to get notified when mouse moved from one header item to another item

Post by kcvinu »

Hi all,
I am playing with the header control of a ListView. I wonder how to get notified when mouse pointer moves from one header column to another. Say, I have 3 columns in my listview. If I put the mouse pointer to 2nd column header, I will get WM_NMHITTEST & WM_SETCURSOR messages. But if I move the mouse pointer to 3rd column header, I will get the same two messages. So there is no way to know which header is under mouse pointer. I have tried to send the HDM_GETFOCUSEDITEM message to the header control, but it always returns a zero. Somebody please tell me how to solve this.
Edit : Some extra info
I have sublcassed ListView's wndProc and Header's WndProc. So I have two WndProc functions. That's why I am getting WM_NMHITTEST & WM_SETCURSOR when I move the mouse pointer.
Last edited by kcvinu on Jun 22, 2022 21:20, edited 1 time in total.
kcvinu
Posts: 232
Joined: Oct 07, 2015 16:44
Location: Keralam, India

Re: How to get notified when mouse moved from one header item to another item

Post by kcvinu »

For the future readers of this post.
I have solved this problem by myself. After plenty of hours relentless experiments, at last I found the right solution. We can use either owner draw or custom draw for this. That doesn't matter. These are the steps involved.
  • 1. Subclass header control of the ListView. So that we can handle header's messages specially.
    2. In the WndProc function, handle WM_MOUSEMOVE and store the x, y points in a POINT struct.
    3. Write a for loop and inside the loop, get each header item's rect by sending HDM_GETITEMRECT message to header control.
    4. Use PtInRect function to check if the mouse pointer is upon that particular rect.
    5. If so, keep the header item index in a variable and call InvalidateRect function. This will resulted in our drawing function. Inside the drawing function, write an If statement to check the header index number and if we got the index that matching our variable, change the HBRUSH color.
    6. Last, but not least, In the WndProc function, handle the WM_MOUSELEAVE message and clear our flag variable. Then call InvalidateRect function again.

I have experimented this in both owner draw & custom draw. Both are success.
EDIT : But this is really strange that microsoft did not implemented a notification for header control mouse moving over different columns.

EDIT 2 : After two days, I happened to see a message named HDM_HITTEST. So if we use that, we don't need to use a loop to iterate over our columns. This message needs a HD_HITTESTINFO struct pointer as it's LPARAM parameter. But we need to fill the pt member of this struct. And when the message returns, the struct's iItem member become the index of header control. So we can set the flag for this index and use InvalidateRect to repaint the header. This is better method, as it is doing less job to get the header index. No need to loop through the columns, no need to get the item rect of header control, no need to inspect the rect with PtInRect function.
Post Reply