多个类似动态创建的命令按钮的操作 [英] Actions for multiple similar dynamically created command buttons

查看:145
本文介绍了多个类似动态创建的命令按钮的操作的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在Excel VBA中编写一个程序,基本上将从一个文本框和一个命令按钮开始,命令按钮将在其下方创建一个新的文本框和命令按钮,该命令按钮又将创建一个新的文本框,命令按钮等。希望你跟随那个混乱。



我可以创建初始按钮没有问题(它必须动态创建,所以它有机会被删除)。然后我的问题是创建 click()事件处理程序。我需要所有的 click()事件来做同样的事情,但命名新的对象相对于自己的名字。这一切都是我的头脑,我真的很感激一点帮助。



随时询问具体的信息,但我没有真正能够包住我的头

解决方案

创建一个名为CEventClass的定制类模块(Insert-Class Module, F4更改名称)。在课程模块中输入此代码

 '这些代码声明为WithEvents,所以事件是
'暴露给我们
Public WithEvents cmdEvent As MSForms.CommandButton
Public WithEvents tbxEvent As MSForms.TextBox


'这将为任何控件
分配给cmdEvent
Private Sub cmdEvent_Click()

MsgBox cmdEvent.Caption

End Sub

'这将为任何控件
'分配给tbxEvent
Private Sub tbxEvent_Change()

如果Len(tbxEvent.Text)< 6然后
tbxEvent.BackColor = vbYellow
Else
tbxEvent.BackColor = vbWhite
如果

End Sub

现在创建一个没有控件的Userform。将此代码放在窗体的代码模块中

 '这些将保持
'范围内的类实例只要表单被加载
私有mEventButtons作为集合
私有mEventTexts作为集合

私有子UserForm_Initialize()

Dim cmd As MSForms.CommandButton
Dim txt As MSForms.TextBox
Dim clsEventClass As CEventClass

设置mEventButtons =新集合
设置mEventTexts =新集合

'创建两个命令按钮
设置cmd = Me.Controls.Add(Forms.CommandButton.1,FirstName)
cmd.Top = 10
cmd.Left = 10
cmd.Caption = First
'创建一个新的CEventClass实例,
'将该按钮分配给cmdEvent
设置clsEventClass =新的CEventClass
设置clsEventClass.cmdEvent = cmd
mEventButtons。添加clsEventClass

设置cmd = Me.Controls.Add(Forms.CommandButton.1,SecondName)
cmd.Top = 50
cmd.Left = 10
cmd.Caption =Second
设置clsEventClass =新的CEventClass
设置clsEventClass.cmdEvent = cmd
mEventButtons.Add clsEventClass

'创建两个文本框并将它们分配给新的实例
'
设置txt = Me.Controls.Add(Forms.TextBox.1 ,ThirdName)
txt.Top = 10
txt.Left = 150
设置clsEventClass =新的CEventClass
设置clsEventClass.tbxEvent = txt
mEventTexts.Add clsEventClass

设置txt = Me.Controls.Add(Forms.TextBox.1,FourthName)
txt.Top = 50
txt.Left = 150
设置clsEventClass =新的CEventClass
设置clsEventClass.tbxEvent = txt
mEventTexts.Add clsEventClass

End Sub

现在,当您运行表单时,如果您点击/更改控件,这两个事件将触发。



您可以请注意,t没有AfterUpdate事件extbox。该事件实际上并不是一个文本框事件,而是一个文本框的控件容器的事件,因此您不能以这种方式公开它。这就是我喜欢在设计时创建所有控件的一个原因,并根据需要隐藏或取消隐藏它们。我仍然可以使用WithEvents的一些控件,所以我不必重复代码这么多。但是对于像TextBox_AfterUpdate这样的事情,我只是在设计时创建所有的事件过程。



更新:



如果你想要事件创建新的按钮,你必须做更多的事情。首先,您必须将该集合暴露在userform之外。您将其添加到您的Userform模块中

 公共属性获取EventButtons()作为集合
设置EventButtons = mEventButtons
结束属性

然后更改您的命令按钮事件代码以创建一个新按钮

  Private Sub cmdEvent_Click()

Dim cmd As MSForms.CommandButton
Dim clsEventClass As CEventClass

设置cmd = cmdEvent.Parent.Controls.Add(Forms.CommandButton.1,cmdEvent.Caption&1)
cmd.Top = cmdEvent.Top + 40
cmd。 Left = cmdEvent.Left
cmd.Caption = cmdEvent.Caption& 1
设置clsEventClass =新的CEventClass
设置clsEventClass.cmdEvent = cmd
cmdEvent.Parent.EventButtons.Add clsEventClass

End Sub

这将创建一个新的按钮40点以下,以点击的方式。你不说你的逻辑是命名或定位,所以我认为你可以工作。使用cmdEvent.Parent获取对Userform的引用。


I am writing a program in Excel VBA that will basically start with one textbox and one command button, and the command button will create a new textbox and command button underneath it, and that command button will in turn create a new textbox and command button, and so on. Hope you followed that mess.

I can create the initial button no problem (it has to be dynamically created so it has the opportunity to be deleted later). My problem is then with creating the click() event handler. I need all the click() events to do the same thing, but name the new Objects relative to its own name. This is all blowing my mind, I would really appreciate a little help.

Feel free to ask for specific information, but I haven't really been able to wrap my head around the topic well enough to write some test code yet.

解决方案

Create a custom class module called CEventClass (Insert - Class Module, F4 to change the name). Type this code into the class module

'These are declared WithEvents so the events are
'exposed to us
Public WithEvents cmdEvent As MSForms.CommandButton
Public WithEvents tbxEvent As MSForms.TextBox


'This will fire for any control
'assigned to cmdEvent
Private Sub cmdEvent_Click()

    MsgBox cmdEvent.Caption

End Sub

'This will fire for any control
'assigned to tbxEvent
Private Sub tbxEvent_Change()

    If Len(tbxEvent.Text) < 6 Then
        tbxEvent.BackColor = vbYellow
    Else
        tbxEvent.BackColor = vbWhite
    End If

End Sub

Now create a Userform with no controls on it. Put this code in the form's code module

'These will keep the class instances in
'scope for as long as the form is loaded
Private mEventButtons As Collection
Private mEventTexts As Collection

Private Sub UserForm_Initialize()

    Dim cmd As MSForms.CommandButton
    Dim txt As MSForms.TextBox
    Dim clsEventClass As CEventClass

    Set mEventButtons = New Collection
    Set mEventTexts = New Collection

    'Create two commandbuttons
    Set cmd = Me.Controls.Add("Forms.CommandButton.1", "FirstName")
    cmd.Top = 10
    cmd.Left = 10
    cmd.Caption = "First"
    'Create a new instance of CEventClass and
    'assign the button to cmdEvent
    Set clsEventClass = New CEventClass
    Set clsEventClass.cmdEvent = cmd
    mEventButtons.Add clsEventClass

    Set cmd = Me.Controls.Add("Forms.CommandButton.1", "SecondName")
    cmd.Top = 50
    cmd.Left = 10
    cmd.Caption = "Second"
    Set clsEventClass = New CEventClass
    Set clsEventClass.cmdEvent = cmd
    mEventButtons.Add clsEventClass

    'Create two textboxes and assign them to new instances
    'of the class
    Set txt = Me.Controls.Add("Forms.TextBox.1", "ThirdName")
    txt.Top = 10
    txt.Left = 150
    Set clsEventClass = New CEventClass
    Set clsEventClass.tbxEvent = txt
    mEventTexts.Add clsEventClass

    Set txt = Me.Controls.Add("Forms.TextBox.1", "FourthName")
    txt.Top = 50
    txt.Left = 150
    Set clsEventClass = New CEventClass
    Set clsEventClass.tbxEvent = txt
    mEventTexts.Add clsEventClass

End Sub

Now when you run the form, those two events will fire if you click/change the control.

You may note that there is no AfterUpdate event for the textbox. That event is not actually a textbox event, but an event of the control container for the textbox, so you can't expose it this way. That's one reason I prefer to create all the controls at design time and hide or unhide them as needed. I still might use WithEvents for some controls just so I don't have to repeat code so much. But for things like TextBox_AfterUpdate, I just create all the event procedures at design time.

Update:

If you want the event to create new buttons, you have to do a couple more things. First, you have to expose the collection outside of the userform. You add this to your Userform module

Public Property Get EventButtons() As Collection
    Set EventButtons = mEventButtons
End Property

Then you change your commandbutton event code to create a new button

Private Sub cmdEvent_Click()

    Dim cmd As MSForms.CommandButton
    Dim clsEventClass As CEventClass

    Set cmd = cmdEvent.Parent.Controls.Add("Forms.CommandButton.1", cmdEvent.Caption & "1")
    cmd.Top = cmdEvent.Top + 40
    cmd.Left = cmdEvent.Left
    cmd.Caption = cmdEvent.Caption & "1"
    Set clsEventClass = New CEventClass
    Set clsEventClass.cmdEvent = cmd
    cmdEvent.Parent.EventButtons.Add clsEventClass

End Sub

This creates a new button 40 points below whichever was clicked. You don't say what your logic is for naming or positioning, so I assume you can work that out. Use cmdEvent.Parent to get a reference to the Userform.

这篇关于多个类似动态创建的命令按钮的操作的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆