Results 1 to 6 of 6

Thread: Visual Basic 2015 dictionary with listbox

Hybrid View

  1. #1

    Thread Starter
    New Member
    Join Date
    Jul 2018
    Posts
    4

    Question Visual Basic 2015 dictionary with listbox

    Hello,

    I would like to show all content of a Dictionary Object in a listbox. However, when I do so, the content of my Dictionary is shown between brackets [ ]. What am I doing wrong?


    Dim MyDictionary As New Dictionary(Of String, String)

    MyDictionary.Add("abc", "def")
    listbox.DataSource = New BindingSource(MyDictionary, Nothing)


    The result of the code above is shown in the listbox as [abc,def]

    Why are these [] shown? What am I doing wrong?

  2. #2
    Super Moderator dday9's Avatar
    Join Date
    Mar 2011
    Location
    South Louisiana
    Posts
    11,715

    Re: Visual Basic 2015 dictionary with listbox

    Whenever you bind the Dictionary, whichever you want to display (key or value) in the ListBox you should specify as the DisplayMember and whichever you want to return when calling SelectedValue you should specify as the ValueMember. Something like this:
    Code:
    Dim MyDictionary As New Dictionary(Of String, String)
    
    MyDictionary.Add("abc", "def")
    With ListBox1
        .DataSource = New BindingSource(MyDictionary, Nothing)
        .DisplayMember = "Key"
        .ValueMember = "Value"
    End With
    "Code is like humor. When you have to explain it, it is bad." - Cory House
    VbLessons | Code Tags | Sword of Fury - Jameram

  3. #3
    Super Moderator jmcilhinney's Avatar
    Join Date
    May 2005
    Location
    Sydney, Australia
    Posts
    110,301

    Re: Visual Basic 2015 dictionary with listbox

    Quote Originally Posted by dday9 View Post
    Whenever you bind the Dictionary, whichever you want to display (key or value) in the ListBox you should specify as the DisplayMember and whichever you want to return when calling SelectedValue you should specify as the ValueMember. Something like this:
    Code:
    Dim MyDictionary As New Dictionary(Of String, String)
    
    MyDictionary.Add("abc", "def")
    With ListBox1
        .DataSource = New BindingSource(MyDictionary, Nothing)
        .DisplayMember = "Key"
        .ValueMember = "Value"
    End With
    Just a small note on that: it's better to set the DataSource last. That's because doing so means that the binding is done as it should that one and only time whereas, if you set the DataSource first, the binding is then done once without a DisplayMember and again when you set the DisplayMember. The only time I have ever found a reason to set the DataSource first is when binding to a CheckedListBox, which doesn't officially support data-binding and behaves oddly if you set the DataSource last.

  4. #4

    Thread Starter
    New Member
    Join Date
    Jul 2018
    Posts
    4

    Re: Visual Basic 2015 dictionary with listbox

    Hi jmcilhinney, I have tried this code but I end up seeing only the "key". I would like to display both the key and the value next to eachother in the listbox. Is that possible?

  5. #5
    Super Moderator jmcilhinney's Avatar
    Join Date
    May 2005
    Location
    Sydney, Australia
    Posts
    110,301

    Re: Visual Basic 2015 dictionary with listbox

    It's possible to display that data but not by simply binding the Dictionary. The ListBox can either display the result of calling ToString on each item or it can display the result of calling ToString on one property of each item. Those are your only options. If you want to display something other than that then you have to either load the data manually or else create another list that exposes the data you want. That could be another Dictionary, e.g.
    vb.net Code:
    1. Private ReadOnly numbersByPlace As New Dictionary(Of String, String) From {{"First", "One"},
    2.                                                                            {"Second", "Two"},
    3.                                                                            {"Third", "Three"}}
    4.  
    5. Private Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load
    6.     Dim modifiedDictionary = numbersByPlace.ToDictionary(Function(kvp) kvp.Key,
    7.                                                          Function(kvp) $"{kvp.Key} - {kvp.Value}")
    8.  
    9.     BindingSource1.DataSource = modifiedDictionary
    10.  
    11.     With ListBox1
    12.         .DisplayMember = "Value"
    13.         .ValueMember = "Key"
    14.         .DataSource = BindingSource1
    15.     End With
    16. End Sub
    17.  
    18. Private Sub ListBox1_SelectedIndexChanged(sender As Object, e As EventArgs) Handles ListBox1.SelectedIndexChanged
    19.     Dim place = CStr(ListBox1.SelectedValue)
    20.  
    21.     If place IsNot Nothing Then
    22.         Dim number = numbersByPlace(place)
    23.  
    24.         MessageBox.Show(number)
    25.     End If
    26. End Sub

  6. #6
    Super Moderator jmcilhinney's Avatar
    Join Date
    May 2005
    Location
    Sydney, Australia
    Posts
    110,301

    Re: Visual Basic 2015 dictionary with listbox

    Quote Originally Posted by ON3WVS View Post
    Why are these [] shown? What am I doing wrong?
    The reason you see what you see is that, if you don't set the DisplayMember, the control simply calls ToString on each item to get the text to display for that item. What you're seeing it the result of the KeyValuePair(Of String, String).ToString method. As suggested, if you want the value of a specific member to be displayed for each item then you have to specify that member.

    By the way, while it's not wrong to create the BindingSource in code like that, there's generally no good reason not to create the BindingSource in the designer and then simply set its DataSource property in code.

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  



Click Here to Expand Forum to Full Width