我正在尝试在运行时向工作表添加一个按钮。此按钮应该只显示在运行时也创建的不同工作表。我添加了这样的按钮:
Dim btnShowTable
Set btnShowTable = ActiveSheet.Buttons.Add(rowRange.Left + 10, rowRange.Top + 10, rowRange.Width - 20, rowRange.Height - 20)
btnShowTable.Caption = "Show table data"
btnShowTable.OnAction = AddClickHandler_ShowSheet("ClickModule", "TableView", tableSheet)
Function AddClickHandler_ShowSheet(ByVal moduleName As String, ByVal btnName As String, ws As Worksheet)
Dim methodName As String
methodName = btnName & "_" & AddClickHandler_GetId() & "_Click"
Dim LineNum As Long
Dim VBCodeMod As CodeModule
Set VBCodeMod = ThisWorkbook.VBProject.VBComponents(moduleName).CodeModule
With VBCodeMod
LineNum = .CountOfLines + 1
.InsertLines LineNum, _
"Sub " & methodName & "()" & Chr(13) & _
" " & ws.CodeName & ".Select" & Chr(13) & _
"End Sub"
End With
AddClickHandler_ShowSheet = moduleName & "." & methodName
End Function
创建按钮的功能在一个模块中,而AddClickHandler_ShowSheet在另一个模块中。
我的想法是,我将拥有包含所有这些点击处理程序的单独模块,以便我可以轻松删除所有这些。 这没问题。创建处理程序并按钮按预期工作。我遇到的问题是,当调用此InsertLines方法时,包含创建按钮的函数的模块中的所有模块变量都将丢失。 我有4个模块变量
Dim xmldoc As New MSXML2.DOMDocument
Dim xmlDataMap() As DataNode
Dim xmlDataMapLast As Integer
Dim xmlTables As Collection
在调用InsertLines之后,除了包含正确值14的xmlDataMapLast之外,所有这些都变为空。
如果我在单步调用InserLines时尝试调试此方法,则会收到错误“此时无法进入中断模式”。在我的功能结束之前我无法调试任何东西。如果我注释掉对AddClickHandler_ShowSheet的调用,我的变量保持不变,所以它必须是与该调用相关的东西。
我是在尝试实现不可能的,还是我只是以错误的方式做到了?
答案 0 :(得分:4)
模块重置并不奇怪 实际上,我也希望值类型能够重置。这有点意外 他们活了下来。
为什么需要在用于代码生成的模块中存储变量?
将它们存储在单独的模块中,仅使用此模块进行代码生成。
说完了,你为什么要先动态添加代码?
OnAction
支持参数:
Sub asdff()
Worksheets(1).Buttons(1).OnAction = "'Module1.ParametrizedHandler 5, ""Hi there""'"
End Sub
Public Sub ParametrizedHandler(ByVal foo As Long, ByVal bar As String)
MsgBox foo, vbInformation, bar
End Sub
请注意,调用字符串中没有括号,并且单引号围绕它。