Subitems in a Listview Control

G

Guest

Hello,

I've noticed through searching this group's previous posts that one can get
the item the mouse is over in a listview control but I did not see how to get
the subitem the mouse is over. Is this possible?

I intend on replacing an ActiveX grid with a listview control from a VB6
application that I've upgraded to VB .NET. The existing functionlality uses
the mouseover event of the grid to display specific information within
individual cells of the grid.

Thanks!
Jack
 
J

J L

Hi Jack,
Here is the code someone shared with me previously and I am passing
along to you. I use it extenstively...you should be able to cut and
paste to get it to work.

Structure RECT
Public left As Integer
Public top As Integer
Public right As Integer
Public bottom As Integer
End Structure 'RECT

Declare Auto Function SendMessage Lib "user32.dll" (ByVal hWnd As
IntPtr, ByVal wMsg As Integer, ByVal wParam As Integer, ByRef lParam
As RECT) As Integer

Public Function GetListViewSubItem(ByVal listView1 As ListView,
ByVal pt As Point) As Integer
Try
'
'***** IMPORTANT ***** The ListView must be set for FullRowSelect!!
'
Const LVM_FIRST As Integer = &H1000
Const LVM_GETSUBITEMRECT As Integer = LVM_FIRST + 56
Const LVIR_BOUNDS As Integer = 0

Dim myrect As RECT
Dim lvitem As ListViewItem = listView1.GetItemAt(pt.X, pt.Y)
If lvitem Is Nothing AndAlso listView1.SelectedItems.Count > 0
Then
lvitem = listView1.SelectedItems(0)
End If
Dim intLVSubItemIndex As Integer = -1
Dim LVSubItem As ListViewItem.ListViewSubItem = Nothing

If Not (lvitem Is Nothing) Then
Dim intSendMessage As Integer
Dim i As Integer
For i = 1 To lvitem.SubItems.Count - 1
LVSubItem = lvitem.SubItems(i)
myrect = New RECT
myrect.top = i
myrect.left = LVIR_BOUNDS
intSendMessage = SendMessage(listView1.Handle,
LVM_GETSUBITEMRECT, lvitem.Index, myrect)
If pt.X < myrect.left Then
LVSubItem = lvitem.SubItems(0)
intLVSubItemIndex = 0
Exit For
ElseIf pt.X >= myrect.left And pt.X <= myrect.right
Then
intLVSubItemIndex = i
Exit For
Else
LVSubItem = Nothing
End If
Next i
End If
If LVSubItem Is Nothing OrElse lvitem Is Nothing Then
intLVSubItemIndex = -1
End If
Return intLVSubItemIndex
Catch ex As Exception
ErrHandler("MarymonteUtilities - GetListViewSubItem", ex)
End Try
End Function
 
G

Guest

Thank you for the code. I did cut and paste it into a test application and
the coordinates for subitems seems to be off a little bit. I'm calling the
procedure you provided in the MouseHover event below:

Private Sub grdData_MouseHover(ByVal sender As Object, ByVal e As
System.EventArgs) Handles grdData.MouseHover
Me.ToolTip1.SetToolTip(grdData, GetListViewSubItem(grdData,
sender.mouseposition))
End Sub

grdData is the listview control. The subitem index that is shown in the tool
tip seems to be off by one column. It seems to be looking at the column to
the right of the column where the mouse is hovering over. Am I doing
something wrong?

Jack
 
J

J L

I dont find a Sender.Mouseposition property in the hover event.

I set the mouse location in the mouse move event and also display the
associated tip in that event.

Those are the only differences I can see.

John

So perhaps it is in the hover and sender.mouseposition
 
G

Guest

Nevermind. I was passing in the incorrect Point. I was passing in the
mouseposition of the listview control when I should have been sending in the
x and y coordinates of the event argument as a new point. Here is the code
for anyone with this same issue (I also moved the code to MouseOver from
MouseHover):

Private Sub GridData_MouseMove(ByVal sender As System.Object, ByVal e As
System.Windows.Forms.MouseEventArgs) Handles grdData.MouseMove
Dim lvSubItem As ListViewItem.ListViewSubItem
lvSubItem = GetListViewSubItem(grdData, New Point(e.X, e.Y))
If Not lvSubItem Is Nothing Then
Me.ToolTip1.SetToolTip(grdData, lvSubItem.Text)
Else
Me.ToolTip1.RemoveAll()
End If
End Sub


P.S. I also modified the GetListViewSubItem procedure to pass back the
subitem object instead of the index.

Thanks for you help!!

Jack
 
J

J L

Good news Jack. As to passing back the subitem or the index, I use the
index because I want to access both the item and the column title. So
the index is useful in that case.

John
 
G

Guest

John, it's a funny thing ... I got to my desk this morning to work on this
project and came across another instance where I need to use the code you
provided. As it turns out, I need the index returned and not just the
subitem. If forgot that the subitem doesn't provide an index to its position
in the item. So, the code is back to where you originally intended it to be.
I should have assumed the decision to send back the subitem or index was well
thought out.

Thanks again. It's a very useful chunk of code.

Jack
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top