【问题标题】:How to make the Combobox item list dynamic?如何使组合框项目列表动态化?
【发布时间】:2016-11-15 14:30:58
【问题描述】:

我在工作表上使用了“生成”按钮。当我单击按钮时,会出现一个弹出窗口(表单),其中包含两个组合框。根据第一个组合框中的选择,填充第二个组合框选项列表。

对于第一个组合框,当我对项目值进行硬编码时,它可以正常工作。表单代码如下:

Private Sub UserForm_Initialize()

With ComboBox_DL
    .AddItem "DL1"
    .AddItem "DL2"
End With

End Sub

我尝试通过使用以下表单代码从 excel 工作表中的列中获取组合框项目值来使此项目列表动态化:

Private Sub UserForm_Initialize()

With ComboBox_DL
For Each c In ActiveSheet.Range(Range("AE"), Range("AE").End(xlDown))
 .AddItem c.Value
Next
End With

End Sub

但上面的代码抛出错误:运行时错误'1004':对象'_Global'的方法'Range'失败

I modified the code adding sheet details: 
With ComboBox_DL
    For Each c In ThisWorkbook.Worksheets("Business_Input_Data").Range(Range("AE"), Range("AE").End(xlDown))
        .AddItem c.Value
Next

它仍然会抛出相同的错误。

有人可以帮忙吗?另外,我想知道如何在combobox1中查找与选择对应的值并填充combobox2中的列表?

【问题讨论】:

    标签: vba excel combobox


    【解决方案1】:

    如果您的组合框条目是工作表上的列表,则根本不需要使用 VBA 来填充它们。相反,您可以创建一个动态命名范围,并将其用作组合框的行源。

    假设您的列表从 Sheet3 的单元格 A1 开始。转到公式 |名称管理器创建一个命名范围。给它起一个有用的名称,例如“Combo”,然后将以下公式放入 RefersTo:=OFFSET(Sheet3!$A$1,0,0,COUNTA(Sheet3!$A:$A),1) 保存并关闭命名范围对话框。

    在组合框的属性中,查找“RowSource”行。将其设置为 =Combo,或您用于命名范围的任何名称。

    对列表的任何更改,包括加长或缩短,现在都将立即自动反映在组合框中。

    编辑添加:

    要使用在第一个组合框中选择的值来确定在第二个组合框中使用哪个列表,我们需要做两件事。

    首先是为第一个列表中的所有可能选择创建命名范围:

    在图片中,A 列是我们第一个组合框的来源;其他列包含第二个组合框的可能来源。

    然后我们只需在第一个组合框的 Change 事件中添加一点代码:

    Private Sub ComboBox1_Change()
        Me.ComboBox2.Value = ""
        Me.ComboBox2.RowSource = "=" & Me.ComboBox1.Value
    End Sub
    

    只要 ComboBox1 更改,此代码就会触发。首先它清除 ComboBox2 中的所有现有值,然后将 ComboBox2 的行源属性设置为 = 符号和在第一个框中选择的任何值的组合。由于这些值也是命名范围,因此第二个框现在将使用选定的命名范围作为其列表源。

    如果需要,您可以添加更多级别的级联选项,每个选项都有不同的命名范围。不过,不止几个级别可能会变得无法管理 - 在这一点上,我们可能想看看另一种方法。

    【讨论】:

    • 谢谢 Werf。如何显示第二个组合框,该组合框将包含基于第一个组合框中的选择的列表?
    • 通常,如果我们使用数据验证下拉菜单执行此操作,我们只会说根据您的第一个范围中的可能值创建其他命名范围,并使用指向结果的间接公式第一个作为其他来源。使用表单上的组合框,它有点复杂;我将编辑为您添加一些代码。
    【解决方案2】:

    尚未对此进行测试,因为我没有创建用户表单以在相同条件下进行测试,但应该可以进行细微改动。

    Dim n As Long
    n = Sheets("Business_Input_Data").Cells(Rows.Count, "AE").End(xlUp).Row
    
    With ComboBox_DL
        For Each c In ThisWorkbook.Worksheets("Business_Input_Data").Range("AE" & n)
            .AddItem c.Value
    Next
    

    【讨论】:

    • 谢谢 mo.h 如何显示第二个组合框,该组合框将包含基于列表的第一个组合框中的选择?假设我有一个用于 DL 名称和相应的 combobox2 列表选项的表?
    • 没问题!如果您发现它有用,请将其标记为答案:)。关于你上面的问题,你的意思是什么?请澄清
    • 在同一个表单中,我有另一个组合框 2,它根据我在组合框 1 中选择的内容列出值。假设 DL1 对应于 A1、B1、C1 项。而DL2对应A2、B2、C2。如果我在组合框 1 中选择 DL1,组合框应该只列出选项 A1、B1 和 C1。同样,对于在 combobox1 中选择的 DL2,combbox2 应该列出 A2、B2 和 C2。
    【解决方案3】:

    您缺少“AE”中的行索引 此外,在任何 Range 参考中始终使用明确的工作表限定

    Private Sub UserForm_Initialize()
        Dim c As Range
    
        With ComboBox_DL
            For Each c In For Each c In ThisWorkbook.Worksheets("Business_Input_Data").Range(ThisWorkbook.Worksheets("Business_Input_Data").Range("AE1"), ThisWorkbook.Worksheets("Business_Input_Data").Range("AE1").End(xlDown))
             .AddItem c.Value
            Next
        End With
    End Sub
    

    但更优雅的解决方案是:

    Private Sub UserForm_Initialize()        
        With ThisWorkbook.Worksheets("Business_Input_Data")
            ComboBox_DL.RowSource = .Range("AE1", .Range("AE1").End(xlDown)).Address
        End With        
    End Sub
    
    
    Private Sub UserForm_Initialize()        
        With ThisWorkbook.Worksheets("Business_Input_Data")
            ComboBox_DL.List = .Range("AE1", .Range("AE1").End(xlDown)).Value
        End With        
    End Sub
    

    地点:

    • 前一个绑定你的ComboBox列表到地址为ComboBoxRowSource属性的范围值

    • 后者将给定范围的值作为Combobox

    【讨论】:

    • 谢谢。如何根据组合框1中的选择仅填充组合框2中的特定值?
    • 这是一个新问题,然后发布一个新问题
    【解决方案4】:

    这是一种使用一列范围内的电子邮件动态更新组合框的解决方案。

        Dim c As Range
    
    ComboBox1.Value = ""
    ComboBox1.Clear
    For Each c In Sheets("emails").Range("F5:F5000")
        If c Like "*@*" Then
            ComboBox1.AddItem c
        End If
    Next
    

    'ComboBox.Value' 设置初始值。 'ComboBox.Clear' 清除组合框中的前几行。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2013-08-09
      • 1970-01-01
      • 2013-12-05
      • 1970-01-01
      • 2011-07-31
      • 2020-09-03
      • 1970-01-01
      • 2012-03-10
      相关资源
      最近更新 更多