单击“类模块未触发2.0”中的“事件”

时间:2018-01-10 11:44:18

标签: vba class module

我有一个类似的问题,如以下链接所述:Click Event in Class Module Not Firing

(没有代表在那里发表评论并要求澄清,所以提出了一个新问题)

我的设置如下:

Userform_Initialize对模块中的Sub进行调用,为该Userform创建ComboBox,这些ComboBox被设置为类模块。

如果我理解链接中给出的答案,则在显示用户表单之前忘记ComboBox和类模块之间的连接,因此不会触发操作。不幸的是,我无法让它发挥作用。

我想知道是否有人可以指定链接中给出的答案。我在哪里放置“Option Explicit”和“Private clsLabel As UserFormLabelLink”?我已经尝试了几个位置,但每次遇到不同的错误(编译错误)。

(当我在创建这些ComboBox的模块中放置UserForm.Show时,操作会触发,但这会在Userform的稍后阶段产生91错误。)

如果有人可以提供帮助,我们将不胜感激!

编辑 - 这是代码

模块

Dim inputComboH As cComboHandler
Set collInputCombo = New Collection
Dim userformCombo As ComboBox

Set userformCombo = UserForm1.MultiPage1.Page1.Controls("Frame1").Add("Forms.ComboBox.1")
            With userformCombo
                .Name = "ComboBox"
                'Add items to the combobox
                For k = 0 To 5
                    .AddItem "Item" & k
                Next k


                    Set inputComboH = New cComboHandler
                    Set inputComboH.inputComboH = userformCombo
                    collInputCombo.Add inputComboH


            End With

类模块cComboHandler

Public WithEvents inputComboH As MSForms.ComboBox
Public Sub inputComboH_Click()
    MsgBox "Clicked"
End Sub

1 个答案:

答案 0 :(得分:0)

Option Explicit应放在每个模块/类的顶部。它会阻止您使用未声明的变量。没有Option Explicit,此代码有效。

Sub Example1()

    ' Ctrl + G will open the immediate window, if closed.
    ' You'll need this to view the output.
    myMessage = "Hello World"
    Debug.Print myMessage
End Sub

虽然您从未明确声明myMessage,但它是为您创建的。

添加Option Explicit会阻止相同的代码运行。你会收到一个错误:

  

编译错误:

     

未定义变量

Option Explicit

Sub Example1()

    ' To fix add "Dim myMessage As String" above this line.
    ' The next line is responsible for the error.
    myMessage = "Hello World"
    Debug.Print myMessage
End Sub

这可以帮助您避免细微的错误。在此示例中,如果没有显式选项,则拼写错误会创建两个变量。

' myCounter and myCount are meant to be the same
' variable.  The user forgot/mistyped the name the
' second time around, leading to an infinite loop.
'
' You can run this code.
' Press Cntrl + Break to pause/reset to stop.
Sub Exmaple2()

    myCounter = 1
    Do
        Debug.Print myCounter
        myCount = myCount + 1    ' This line contains our "error"
        DoEvents
    Loop Until myCounter = 100
End Sub

您可以从选项菜单(工具>>选项>>需要变量声明)自动向每个模块添加明确选项(这是一个好主意)。

你的第二个问题是关于scope。范围控制变量的访问方式,以及变量的长期存在。当变量离开范围时,它不再是访问它的有效方式。此时,变量被销毁(这可能并不总是技术上真实,但对于实际的原因,这是可以的)。

在子/函数内声明的变量具有局部范围。这意味着只能在声明程序中访问它们。当程序结束时,它们不再被访问,因此被销毁。一旦被销毁,他们所持有的任何价值都会丢失(这就是为什么你的事件不会被激活 - 包含这些事件的对象都会丢失)。

' At the end of this sub, i will always equal 1,
' regardless of the number of times you execute it.
' This is because i is created each time you call the sub, and destroyed when it ends.
' Each new verson of i has a default value of 0, to which we add one.
Sub Example2()

    Dim i As Integer
    i = i + 1
    Debug.Print i
End Sub

现在让我们在模块/类级别声明i。使用模块范围,变量将一直存在,直到整个模块离开范围。这将发生在:

  • 用户按下重置。
  • 遇到End命令。
  • 关闭了父工作簿。
  • 在班级的情况下;班级留下范围。

示例:

' i is declared at the module/class level.
' It's value is maintained between calls to Example3.
Private i As Integer

' Each call to this sub will increment i by 1.
' Call 1 will output 1.
' Call 2 will output 2.
' etc
Sub Example3()

    i = i + 1
    Debug.Print i
End Sub

范围是一个很大的主题,起初可能会让人感到困惑。大多数VBA books都涵盖了这一点。