Home » excel » vba – Excel user form keeps resetting control tip text

vba – Excel user form keeps resetting control tip text

Posted by: admin May 14, 2020 Leave a comment

Questions:

I have a user form in Excel and all of the text boxes have control tip text. Since I have a lot of text boxes and control tip texts that I am reusing in many Excel workbooks, I found it easier to edit the text in a settings sheet then use a macro to assign the text from the sheet to the controls on my form. This gives me the benefit of using find & replace and it’s easier to edit text in a sheet compared to using the properties menu. The macro assigns the control tip text like this:

With formSettings
    .textBox1.ControlTipText = Sheets("Settings").Cells(4, 12).Text
End With

But the behavior is bizarre. When I run the macro then open the form from the interface I see the new control tip text assigned to the controls. But if I close the form and reopen it, it resets back to the previous control tip text. Any idea why this occurs? I have tried saving before opening the form as well as saving, closing the workbook, then reopening, but I can’t seem to figure out why it assigns the control tip text then reverts.

I know that I can force new text at run time by assigning it in the UserForm_Initialize sub, but I’d prefer not to since that would add a layer of inefficiency.

How to&Answers:

You are missing the concept of instance. A UserForm is a class, and classes define the shape/interface of an object. What’s special about a UserForm is that 1) it has a visual designer, and 2) it has a hidden VB_PredeclaredId attribute set to True, which means the class has a default instance.

When you do this:

UserForm1.Show

You are invoking the Show method against the default instance of the form. When that form is closed, the object is destroyed… until it’s automatically created again the next time you reference the UserForm1 default instance.

I know that I can force new text at run time by assigning it in the UserForm_Initialize sub, but I’d prefer not to since that would add a layer of inefficiency.

Not at all. Something, somewhere needs to initialize the form. If your form controls need to be configured at run-time, UserForm_Initialize is the single best possible place to initiate this configuration – it ensures that every time a new instance of the form is created, it’s properly initialized. In the case of an instruction like UserForm1.Show, the handler runs at the . dereferencing operator, just before the Show method is invoked.

The object retains its state as long as it exists. Problem is, “X’ing-out” of the form will destroy the object, and thus reset it to its original, design-time state.

You can prevent the form instance from self-destructing by handling the QueryClose event and setting the Cancel parameter to True when the CloseMode parameter value is VbQueryClose.vbFormControlMenu, and then Hideing the form rather than destroying it – of course you should never Unload the form either.

Dealing with a UserForm becomes much simpler when you control when it’s created, and when it’s destroyed. In other words, when you avoid using its default instance to store any state.

With New UserForm1 ' _Initialize handler runs
    '..setup initial form state here..
    .Show
    '..access form state here..
End With ' _Terminate handler runs, object is destroyed

I wrote articles UserForm1.Show and About Class Modules covering these topics in-depth.