By using this site, you agree to our updated Privacy Policy and our Terms of Use. Manage your Cookies Settings.
459,312 Members | 1,330 Online
Bytes IT Community
+ Ask a Question
Need help? Post your question and get tips & solutions from a community of 459,312 IT Pros & Developers. It's quick & easy.

Listview Question

P: n/a
Hi all,

I want to implement a listview with editable subitems and I assume the
easiest way is to overlay a textbox over the item to be edited.

With this in mind I have come up with:

Using fullrowselect=true in the listview

Private Sub ListView1_ItemSelectionChanged(ByVal sender As Object, _
ByVal e As System.Windows.Forms.ListViewItemSelectionChangedE ventArgs) _
Handles ListView1.ItemSelectionChanged
Dim t As New TextBox
Me.Controls.Add(t)
t.Location = e.Item.Position
t.BringToFront()
End Sub

Unfortunately item.position only enables me to get the position of the first
column. How can I obtain the x position of the subitem that was clicked.

I have searched google, but the only examples I can find are in C++ which I
can't make any sense of.

Thanks,

Martin.
Mar 20 '06 #1
Share this Question
Share on Google+
5 Replies


P: n/a
I have found this VB6 example, but I can't figure out how to convert it to
..net, can anyone help me.

Thanks

'Declarations:
Private Type lvwItemClick
x As Long
y As Long
Flgs As Long
Itm As Long
SubItm As Long
End Type

Private Declare Function SendMessage _
Lib "user32" Alias "SendMessageA" ( _
ByVal hwnd As Long, _
ByVal lMsg As Long, _
ByVal wParam As Long, _
lParam As Any) As Long

Dim lvwClick As lvwItemClick

Private Sub ListView1_MouseDown(Button As Integer, _
Shift As Integer, x As Single, y As Single)

lvwClick .x = x / Screen.TwipsPerPixelX
lvwClick .y = y / Screen.TwipsPerPixelY

SendMessage ListView1.hwnd, 4153, 0, lvwClick

If Button = vbRightButton And lvwClick .Itm = 2 And lvwClick .SubItm = 1
Then _
PopupMenu mnuTest 'poppup menu mnuTest for click on Item 3, SubItem 1.

End Sub
"Martin Horn" <mv****@theinternet.com> wrote in message
news:Gc*****************@newsfe7-win.ntli.net...
Hi all,

I want to implement a listview with editable subitems and I assume the
easiest way is to overlay a textbox over the item to be edited.

With this in mind I have come up with:

Using fullrowselect=true in the listview

Private Sub ListView1_ItemSelectionChanged(ByVal sender As Object, _
ByVal e As System.Windows.Forms.ListViewItemSelectionChangedE ventArgs) _
Handles ListView1.ItemSelectionChanged
Dim t As New TextBox
Me.Controls.Add(t)
t.Location = e.Item.Position
t.BringToFront()
End Sub

Unfortunately item.position only enables me to get the position of the
first column. How can I obtain the x position of the subitem that was
clicked.

I have searched google, but the only examples I can find are in C++ which
I can't make any sense of.

Thanks,

Martin.

Mar 20 '06 #2

P: n/a
I'm working on the same thing... Not yet complete, but it's getting there.

Private Sub lstRules_MouseUp(ByVal sender As Object, ByVal e _
As System.Windows.Forms.MouseEventArgs) Handles lstRules.MouseUp
Dim ThisItem As System.Windows.Forms.ListViewItem
Dim NewBox As Control

If Not (e.Button = Windows.Forms.MouseButtons.Left) Then Exit Sub

ThisItem = lstRules.HitTest(e.X, e.Y).Item
If ThisItem Is Nothing Then
Exit Sub
End If

NewBox = New System.Windows.Forms.TextBox
NewBox.Size = New System.Drawing.Size(lstRules.Columns(1).Width - 10,
12)
NewBox.Text = KeyItem.ItemText
NewBox.Location = New System.Drawing.Point(ThisItem.Position.X + _
lstRules.Columns(0).Width + 2,
ThisItem.Position.Y + 1)

Me.Controls.Add(NewBox)
Me.NewBox.BringToFront
AddHandler NewBox.LostFocus, AddressOf DestroyBox
NewBox.Focus()
End Sub

Private Sub DestroyBox(ByVal sender As Object, ByVal e As System.EventArgs)
If sender IsNot Nothing Then
Me.Controls.Remove(sender)
sender.Dispose()
End If
End Sub

Work in progress: Moving the textbox when the user scrolls the Listview.
If you're interested I can post that bit tomorrow

Hth,
Martin
"Martin Horn" <mv****@theinternet.com> wrote in message
news:Gc*****************@newsfe7-win.ntli.net...
Hi all,

I want to implement a listview with editable subitems and I assume the
easiest way is to overlay a textbox over the item to be edited.

With this in mind I have come up with:

Using fullrowselect=true in the listview

Private Sub ListView1_ItemSelectionChanged(ByVal sender As Object, _
ByVal e As System.Windows.Forms.ListViewItemSelectionChangedE ventArgs) _
Handles ListView1.ItemSelectionChanged
Dim t As New TextBox
Me.Controls.Add(t)
t.Location = e.Item.Position
t.BringToFront()
End Sub

Unfortunately item.position only enables me to get the position of the
first column. How can I obtain the x position of the subitem that was
clicked.

I have searched google, but the only examples I can find are in C++ which
I can't make any sense of.

Thanks,

Martin.

Mar 20 '06 #3

P: n/a
Hi Martin,

I have come up with something similar myself, but I can't see how to easily
adapt it to work with scrolling of the listview, so I would definitely be
interested to see your solution.

Here is my version anyway, which retrieves the text from the any of the 6
subitems in my listview and fills the textbox with it when the user double
clicks the listview subitem.

Note: My example doesn't dynamically create the textbox and I have omitted
the code to remove the textbox.

Private Sub ListView1_MouseDoubleClick(ByVal sender As Object, _
ByVal e As System.Windows.Forms.MouseEventArgs) _
Handles ListView1.MouseDoubleClick
Dim ItemX As ListViewItem
ItemX = ListView1.GetItemAt(e.X, e.Y)
If ItemX Is Nothing Then Exit Sub

Dim col As Integer = GetColumnNumber(e.X)

EditBox.Top = ItemX.Position.Y
EditBox.Left = GetColumnX(e.X) + 2
EditBox.Text = ListView1.SelectedItems(0).SubItems(col).Text
EditBox.Width = ListView1.Columns(col).Width
EditBox.BringToFront()
EditBox.Focus()
End Sub

Private Function GetColumnNumber(ByVal MouseX As Integer) As Integer
If MouseX < GetTotalWidth(0) Then Return -1
If MouseX < GetTotalWidth(1) Then Return 0
If MouseX < GetTotalWidth(2) Then Return 1
If MouseX < GetTotalWidth(3) Then Return 2
If MouseX < GetTotalWidth(4) Then Return 3
If MouseX < GetTotalWidth(5) Then Return 4
If MouseX < GetTotalWidth(6) Then Return 5
End Function

Private Function GetColumnX(ByVal MouseX As Integer) As Integer
If MouseX < GetTotalWidth(0) Then Return 0
If MouseX < GetTotalWidth(1) Then Return GetTotalWidth(0)
If MouseX < GetTotalWidth(2) Then Return GetTotalWidth(1)
If MouseX < GetTotalWidth(3) Then Return GetTotalWidth(2)
If MouseX < GetTotalWidth(4) Then Return GetTotalWidth(3)
If MouseX < GetTotalWidth(5) Then Return GetTotalWidth(4)
If MouseX < GetTotalWidth(6) Then Return GetTotalWidth(5)
End Function

Private Function GetTotalWidth(ByVal Cols As Integer) As Integer
Dim tot As Integer = 0
For n As Integer = 0 To Cols - 1
tot += ListView1.Columns(n).Width
Next
Return tot
End Function

"Martin" <x@y.com> wrote in message
news:ex**************@TK2MSFTNGP09.phx.gbl...
I'm working on the same thing... Not yet complete, but it's getting there.

Private Sub lstRules_MouseUp(ByVal sender As Object, ByVal e _
As System.Windows.Forms.MouseEventArgs) Handles lstRules.MouseUp
Dim ThisItem As System.Windows.Forms.ListViewItem
Dim NewBox As Control

If Not (e.Button = Windows.Forms.MouseButtons.Left) Then Exit Sub

ThisItem = lstRules.HitTest(e.X, e.Y).Item
If ThisItem Is Nothing Then
Exit Sub
End If

NewBox = New System.Windows.Forms.TextBox
NewBox.Size = New System.Drawing.Size(lstRules.Columns(1).Width - 10,
12)
NewBox.Text = KeyItem.ItemText
NewBox.Location = New System.Drawing.Point(ThisItem.Position.X + _
lstRules.Columns(0).Width + 2,
ThisItem.Position.Y + 1)

Me.Controls.Add(NewBox)
Me.NewBox.BringToFront
AddHandler NewBox.LostFocus, AddressOf DestroyBox
NewBox.Focus()
End Sub

Private Sub DestroyBox(ByVal sender As Object, ByVal e As
System.EventArgs)
If sender IsNot Nothing Then
Me.Controls.Remove(sender)
sender.Dispose()
End If
End Sub

Work in progress: Moving the textbox when the user scrolls the Listview.
If you're interested I can post that bit tomorrow

Hth,
Martin
"Martin Horn" <mv****@theinternet.com> wrote in message
news:Gc*****************@newsfe7-win.ntli.net...
Hi all,

I want to implement a listview with editable subitems and I assume the
easiest way is to overlay a textbox over the item to be edited.

With this in mind I have come up with:

Using fullrowselect=true in the listview

Private Sub ListView1_ItemSelectionChanged(ByVal sender As Object, _
ByVal e As System.Windows.Forms.ListViewItemSelectionChangedE ventArgs) _
Handles ListView1.ItemSelectionChanged
Dim t As New TextBox
Me.Controls.Add(t)
t.Location = e.Item.Position
t.BringToFront()
End Sub

Unfortunately item.position only enables me to get the position of the
first column. How can I obtain the x position of the subitem that was
clicked.

I have searched google, but the only examples I can find are in C++ which
I can't make any sense of.

Thanks,

Martin.


Mar 21 '06 #4

P: n/a
I have changed my objective a bit. Since detecting a scroll event in a
Listview requires me to subclass the Listview (MS simply forgot to raise a
scroll event, although it is built in the API) I am going to do it right.
I'm building a subclass of the Listview that allows any kind of control
(checkbox, combobox, datetimepicker, textbox) to be added as subitem.

If you're interested I will publish the code on my site when I'm done.
"Martin Horn" <mv****@theinternet.com> schrieb im Newsbeitrag
news:a8*****************@newsfe2-gui.ntli.net...
Hi Martin,

I have come up with something similar myself, but I can't see how to
easily adapt it to work with scrolling of the listview, so I would
definitely be interested to see your solution.

Here is my version anyway, which retrieves the text from the any of the 6
subitems in my listview and fills the textbox with it when the user double
clicks the listview subitem.

Note: My example doesn't dynamically create the textbox and I have omitted
the code to remove the textbox.

Private Sub ListView1_MouseDoubleClick(ByVal sender As Object, _
ByVal e As System.Windows.Forms.MouseEventArgs) _
Handles ListView1.MouseDoubleClick
Dim ItemX As ListViewItem
ItemX = ListView1.GetItemAt(e.X, e.Y)
If ItemX Is Nothing Then Exit Sub

Dim col As Integer = GetColumnNumber(e.X)

EditBox.Top = ItemX.Position.Y
EditBox.Left = GetColumnX(e.X) + 2
EditBox.Text = ListView1.SelectedItems(0).SubItems(col).Text
EditBox.Width = ListView1.Columns(col).Width
EditBox.BringToFront()
EditBox.Focus()
End Sub

Private Function GetColumnNumber(ByVal MouseX As Integer) As Integer
If MouseX < GetTotalWidth(0) Then Return -1
If MouseX < GetTotalWidth(1) Then Return 0
If MouseX < GetTotalWidth(2) Then Return 1
If MouseX < GetTotalWidth(3) Then Return 2
If MouseX < GetTotalWidth(4) Then Return 3
If MouseX < GetTotalWidth(5) Then Return 4
If MouseX < GetTotalWidth(6) Then Return 5
End Function

Private Function GetColumnX(ByVal MouseX As Integer) As Integer
If MouseX < GetTotalWidth(0) Then Return 0
If MouseX < GetTotalWidth(1) Then Return GetTotalWidth(0)
If MouseX < GetTotalWidth(2) Then Return GetTotalWidth(1)
If MouseX < GetTotalWidth(3) Then Return GetTotalWidth(2)
If MouseX < GetTotalWidth(4) Then Return GetTotalWidth(3)
If MouseX < GetTotalWidth(5) Then Return GetTotalWidth(4)
If MouseX < GetTotalWidth(6) Then Return GetTotalWidth(5)
End Function

Private Function GetTotalWidth(ByVal Cols As Integer) As Integer
Dim tot As Integer = 0
For n As Integer = 0 To Cols - 1
tot += ListView1.Columns(n).Width
Next
Return tot
End Function

"Martin" <x@y.com> wrote in message
news:ex**************@TK2MSFTNGP09.phx.gbl...
I'm working on the same thing... Not yet complete, but it's getting
there.

Private Sub lstRules_MouseUp(ByVal sender As Object, ByVal e _
As System.Windows.Forms.MouseEventArgs) Handles lstRules.MouseUp
Dim ThisItem As System.Windows.Forms.ListViewItem
Dim NewBox As Control

If Not (e.Button = Windows.Forms.MouseButtons.Left) Then Exit Sub

ThisItem = lstRules.HitTest(e.X, e.Y).Item
If ThisItem Is Nothing Then
Exit Sub
End If

NewBox = New System.Windows.Forms.TextBox
NewBox.Size = New System.Drawing.Size(lstRules.Columns(1).Width - 10,
12)
NewBox.Text = KeyItem.ItemText
NewBox.Location = New System.Drawing.Point(ThisItem.Position.X + _
lstRules.Columns(0).Width + 2,
ThisItem.Position.Y + 1)

Me.Controls.Add(NewBox)
Me.NewBox.BringToFront
AddHandler NewBox.LostFocus, AddressOf DestroyBox
NewBox.Focus()
End Sub

Private Sub DestroyBox(ByVal sender As Object, ByVal e As
System.EventArgs)
If sender IsNot Nothing Then
Me.Controls.Remove(sender)
sender.Dispose()
End If
End Sub

Work in progress: Moving the textbox when the user scrolls the Listview.
If you're interested I can post that bit tomorrow

Hth,
Martin
"Martin Horn" <mv****@theinternet.com> wrote in message
news:Gc*****************@newsfe7-win.ntli.net...
Hi all,

I want to implement a listview with editable subitems and I assume the
easiest way is to overlay a textbox over the item to be edited.

With this in mind I have come up with:

Using fullrowselect=true in the listview

Private Sub ListView1_ItemSelectionChanged(ByVal sender As Object, _
ByVal e As System.Windows.Forms.ListViewItemSelectionChangedE ventArgs) _
Handles ListView1.ItemSelectionChanged
Dim t As New TextBox
Me.Controls.Add(t)
t.Location = e.Item.Position
t.BringToFront()
End Sub

Unfortunately item.position only enables me to get the position of the
first column. How can I obtain the x position of the subitem that was
clicked.

I have searched google, but the only examples I can find are in C++
which I can't make any sense of.

Thanks,

Martin.



Mar 21 '06 #5

P: n/a
Although my solution works in the context in which I am using it, I am well
aware that it isn't very efficient and would be very interested in seeing
how you approach the problem, as I am a newbie programmer and what you are
suggesting is well beyond my capabilities at the moment.

If you want to email me the link to your site you can send it to
mvhorn@remove_this_bit.ntlworld.com or post it here instead.

Kind regards,

Martin.

"Martin" <x@y.com> wrote in message
news:%2****************@TK2MSFTNGP09.phx.gbl...
I have changed my objective a bit. Since detecting a scroll event in a
Listview requires me to subclass the Listview (MS simply forgot to raise a
scroll event, although it is built in the API) I am going to do it right.
I'm building a subclass of the Listview that allows any kind of control
(checkbox, combobox, datetimepicker, textbox) to be added as subitem.

If you're interested I will publish the code on my site when I'm done.
"Martin Horn" <mv****@theinternet.com> schrieb im Newsbeitrag
news:a8*****************@newsfe2-gui.ntli.net...
Hi Martin,

I have come up with something similar myself, but I can't see how to
easily adapt it to work with scrolling of the listview, so I would
definitely be interested to see your solution.

Here is my version anyway, which retrieves the text from the any of the 6
subitems in my listview and fills the textbox with it when the user
double clicks the listview subitem.

Note: My example doesn't dynamically create the textbox and I have
omitted the code to remove the textbox.

Private Sub ListView1_MouseDoubleClick(ByVal sender As Object, _
ByVal e As System.Windows.Forms.MouseEventArgs) _
Handles ListView1.MouseDoubleClick
Dim ItemX As ListViewItem
ItemX = ListView1.GetItemAt(e.X, e.Y)
If ItemX Is Nothing Then Exit Sub

Dim col As Integer = GetColumnNumber(e.X)

EditBox.Top = ItemX.Position.Y
EditBox.Left = GetColumnX(e.X) + 2
EditBox.Text = ListView1.SelectedItems(0).SubItems(col).Text
EditBox.Width = ListView1.Columns(col).Width
EditBox.BringToFront()
EditBox.Focus()
End Sub

Private Function GetColumnNumber(ByVal MouseX As Integer) As Integer
If MouseX < GetTotalWidth(0) Then Return -1
If MouseX < GetTotalWidth(1) Then Return 0
If MouseX < GetTotalWidth(2) Then Return 1
If MouseX < GetTotalWidth(3) Then Return 2
If MouseX < GetTotalWidth(4) Then Return 3
If MouseX < GetTotalWidth(5) Then Return 4
If MouseX < GetTotalWidth(6) Then Return 5
End Function

Private Function GetColumnX(ByVal MouseX As Integer) As Integer
If MouseX < GetTotalWidth(0) Then Return 0
If MouseX < GetTotalWidth(1) Then Return GetTotalWidth(0)
If MouseX < GetTotalWidth(2) Then Return GetTotalWidth(1)
If MouseX < GetTotalWidth(3) Then Return GetTotalWidth(2)
If MouseX < GetTotalWidth(4) Then Return GetTotalWidth(3)
If MouseX < GetTotalWidth(5) Then Return GetTotalWidth(4)
If MouseX < GetTotalWidth(6) Then Return GetTotalWidth(5)
End Function

Private Function GetTotalWidth(ByVal Cols As Integer) As Integer
Dim tot As Integer = 0
For n As Integer = 0 To Cols - 1
tot += ListView1.Columns(n).Width
Next
Return tot
End Function

"Martin" <x@y.com> wrote in message
news:ex**************@TK2MSFTNGP09.phx.gbl...
I'm working on the same thing... Not yet complete, but it's getting
there.

Private Sub lstRules_MouseUp(ByVal sender As Object, ByVal e _
As System.Windows.Forms.MouseEventArgs) Handles lstRules.MouseUp
Dim ThisItem As System.Windows.Forms.ListViewItem
Dim NewBox As Control

If Not (e.Button = Windows.Forms.MouseButtons.Left) Then Exit Sub

ThisItem = lstRules.HitTest(e.X, e.Y).Item
If ThisItem Is Nothing Then
Exit Sub
End If

NewBox = New System.Windows.Forms.TextBox
NewBox.Size = New System.Drawing.Size(lstRules.Columns(1).Width - 10,
12)
NewBox.Text = KeyItem.ItemText
NewBox.Location = New System.Drawing.Point(ThisItem.Position.X + _
lstRules.Columns(0).Width + 2,
ThisItem.Position.Y + 1)

Me.Controls.Add(NewBox)
Me.NewBox.BringToFront
AddHandler NewBox.LostFocus, AddressOf DestroyBox
NewBox.Focus()
End Sub

Private Sub DestroyBox(ByVal sender As Object, ByVal e As
System.EventArgs)
If sender IsNot Nothing Then
Me.Controls.Remove(sender)
sender.Dispose()
End If
End Sub

Work in progress: Moving the textbox when the user scrolls the Listview.
If you're interested I can post that bit tomorrow

Hth,
Martin
"Martin Horn" <mv****@theinternet.com> wrote in message
news:Gc*****************@newsfe7-win.ntli.net...
Hi all,

I want to implement a listview with editable subitems and I assume the
easiest way is to overlay a textbox over the item to be edited.

With this in mind I have come up with:

Using fullrowselect=true in the listview

Private Sub ListView1_ItemSelectionChanged(ByVal sender As Object, _
ByVal e As System.Windows.Forms.ListViewItemSelectionChangedE ventArgs)
_
Handles ListView1.ItemSelectionChanged
Dim t As New TextBox
Me.Controls.Add(t)
t.Location = e.Item.Position
t.BringToFront()
End Sub

Unfortunately item.position only enables me to get the position of the
first column. How can I obtain the x position of the subitem that was
clicked.

I have searched google, but the only examples I can find are in C++
which I can't make any sense of.

Thanks,

Martin.



Mar 21 '06 #6

This discussion thread is closed

Replies have been disabled for this discussion.