0

Im making a small vb.net windows form application in which I have 4 ComboBoxes. I would like to add the ComboBoxes to a collection and be able to loop through that collection to refer to each one.

There are other ComboBoxes on the form so I cannot just use the collection for the entire form (the form layout cannot be changed, e.g. to add a container, etc).

I was thinking something like the following:

Public Class Form1
    Dim IoTypeCombos As New ControlCollection(Me) From {Me.IO1_ComboBox, Me.IO2_ComboBox, Me.IO3_ComboBox, Me.IO4_ComboBox}
    Dim IoTypes As New Collection() From {"Out 0", "Out 1", "Input", "Analog"}

    Private Sub Form1_Load(sender As System.Object, e As System.EventArgs) Handles MyBase.Load
        For Each cb As combobox In Me.IoTypeCombos
            FillComboBox(cb, Types)
        Next
    End Sub

    Function FillComboBox(cb As Control, cc As Collection) As Boolean
        Dim cbc As ComboBox = CType(cb, ComboBox)
        If cc.Count = 0 Then
            Return False
        End If
        For Each cn In cc
            cbc.Items.Add(cn)
       Next
       Return True
    End Function

This doesn't raise any exception, BUT it doesn't populate the ComboBoxes either :( The FillComboBox() works perfectly if I pass a single control to it. What am I doing wrong? Thanks

4

2 回答 2

2

此行是非法的:

Public Class Form1
    Dim IoTypeCombos As New ControlCollection(Me) From {Me.IO1_ComboBox, 
                Me.IO2_ComboBox, Me.IO3_ComboBox, Me.IO4_ComboBox }

该代码将在构造函数之前、之前MeION_ComboBox存在之前运行。在这种情况下,结果集合不包含任何内容,因为还没有任何东西可以放入其中。

在其他情况下,在控件存在之前引用它们可能会导致NullReference被抛出,但由于奇怪的错误,它可能不会被报告。发生这种情况时,将跳过其余代码并简单地显示表单。

在任何一种情况下,解决方案都是在表单级别声明您的集合,但是一旦控件确实存在,就在表单加载事件中填充它。我也会使用 Collection(Of T) 代替(一个数组或者List(Of T)也可以工作,但是 OP 使用/询问一个集合):

Imports System.Collections.ObjectModel

Public Class Form1
     Dim IoTypeCombos As Collection(Of ComboBox)  ' form and controls Do No Exist yet

     Public Sub New
         '...
         InitializeComponent()
        ' NOW they exist
     End Sub

     Sub Form_Load
         IoTypeCombos = New Collection(Of ComboBox)
         IoTypeCombos.Add(IO1_ComboBox)
         IoTypeCombos.Add(IO2_ComboBox) 
         ...    

如果你使用 a List(Of ComboBox),你可以用不同的方式填充它:

 ' in the ctor:
 IoTypeCombos = New List(Of ComboBox)({IO1_ComboBox, IO2_ComboBox...})
 ' using AddRange:
 IoTypeCombos.AddRange({IO1_ComboBox, IO2_ComboBox...})
于 2014-11-07T15:02:23.913 回答
0

不确定您是否需要 where 子句,但如果您有其他组合框没有这样的名称并且不希望它们出现在集合中,那么您确实需要它。

Dim IoTypeComboboxes = 
    Me.Controls.OfType(Of Combobox)().Where(Function(cb) cb.Name.StartsWith("IO")).ToList()
于 2014-11-07T15:01:54.803 回答