Excel 2013
I have read several questions that ask this same question and none of those answers seem to be working for me.
I have a userform where a combobox is used to select the number of variables (1, 2, or 3) to be used later in the module. Then an OK button.
I have tried declaring a global variable and making it public in the first line of the module and it seems to work when when click through the macro manually, but when I try to use it as a user would it drops the variable for whatever reason?
Module1
Public variable As Integer
Private Sub Button1_Click()
UserForm1.Show
End Sub
I assume the Button1_Click() has nothing to do with anything, but wanted to show it and confirm it wasn't part of the problem
Userform1
Private Sub UserForm_Activate()
ComboBox1.AddItem 1
ComboBox1.AddItem 2
ComboBox1.AddItem 3
End Sub
user selects 1 2 or 3
Userform1 still
Private Sub OK_Click()
If ComboBox1.ListIndex = -1 Then
MsgBox "Select a number"
Else
variable = Me.ComboBox1.Value
Range("D1").Value = variable'testing
Unload Me
End If
Range("D2").Value = variable 'testing after "Unload Me"???
End Sub
'Module1 again
Sub Macro2()
Range("D3").Select
ActiveCell.FormulaR1C1 = variable
End Sub
When I F8 through UserForm_Activate() --> OK_Click() --> Macro2() it remembers my variable and puts it in cell D3.
If I just click the buttons as a user would and then manually kick off Macro2() it thinks my variable is 0 (not an option) and I get 0 in cell D3, rather than the variable that was selected by the user.
Thanks for your help!
Related
I have created a UserForms with a comboBox (dropdown).
And i have also written sub in a module.
I want to call the userforms in the one the steps of the sub, like a Inputbox.
The userforms
I have written the a Public Sub UserForm_Initialize() in userforms code
Public Sub UserForm_Initialize()
Dim t
UserForm.Show
t = ComboBox1.Value
End Sub
My code in the module :
Sub Ingestion()
Dim x, z
Dim rRange
Sheets("Time Log").Select
x = Range("H300").End(xlUp).Row
If Range("A" & x).Value <> "" Then
z = InputBox("Please confirm the Task type")
Range("B" & x) = z
End If
End Sub
Now I want to change the Input box to the combobox.
but if i call this in the module, it throws an Error :
Sub Test()
Call UserForm_Initialize
End Sub
Sub or Function Not Defined
Basically, i am trying to create a Inputbox with drop down options.
A UserForm_Initialize event gets executed as soon as, surprise, the userform is initialized. So, trying to show the UF when it's already being opened is illogical. Next to that you'd have to refer to the correct UF name, in this case that would result in TaskList.Show.
You open the UF outside of the UF's code module. For example
Sub openUF()
TaskList.Show
End Sub
Then you can execute code inside the UF's module. These are usually bound to objects on the UF, e.g.:
Sub CommandButton_Click() 'in case the UF has a command button and a combobox
MsgBox "You picked '" & Me.ComboBox1.Value & "'.", vbInformation, "Help"
End Sub
I have Userform that have combobox. Combobox picks range from Workbook and inputs picked up result to cell C79 by this VBA:
Private Sub ComboBox1_Change()
ThisWorkbook.Worksheets("Other Data").Range("C79").Value = Me.ComboBox1.Value
End Sub
The problem is when I open Userform for the second time I can't see picked up result in combobox so I have to pick it up again. How to link cell C79 to Private Sub UserForm_Initialize() so that when I open UserForm, value from C79 will be visible in Combobox1?
I have tried:
Private Sub UserForm_Initialize()
ComboBox1.List = ThisWorkbook.Sheets("Other Data").Range("A79:A81").Value ' This one picks the range
'ThisWorkbook.Sheets("Other Data").Range("C79").Value = ReviewForm.ComboBox1.Value
End Sub
To populate a ComboBox control in a UserForm, use the following
Private Sub UserForm_Initialize()
Me.ComboBox1.Value = ThisWorkbook.Sheets("Other Data").Range("C97").Value
End Sub
Alternatively, you could update this value each time the UF is activated:
Private Sub UserForm_Activate()
Me.ComboBox1.Value = ThisWorkbook.Sheets("Other Data").Range("C97").Value
End Sub
Or, you could update the UF's combobox every time the cell value changes. This is not logical however, since you update the cell with the UF. It would activate itself.
I am creating a form out of excel-ActiveX but I have no idea how I can make the command button disabled if all mandatory fields (textbox and combobox) are empty. I've attached the sample form for your reference.
sample LA Form
Use the *_Change event for each control (and optionally the UserForm_Activate event) to set the .Enabled property for the Control Button.
For example, on a simple UserForm with 1 ComboBox (ComboBox1), 2 TextBoxes (TextBox1 and TextBox2) and 1 CommandButton (CommandButton1), the following code will ensure that CommandButton1 is disabled unless there is data in each of the other 3 controls:
Option Explicit
Private Sub CheckMandatoryFields()
'Is a separate sub to make it easy to edit for all Controls at the same time
If Len(TextBox1.Value) > 0 And Len(TextBox2.Value) > 0 And Len(ComboBox1.Value) > 0 Then
CommandButton1.Enabled = True
Else
CommandButton1.Enabled = False
End If
End Sub
Private Sub CommandButton1_Click()
MsgBox "Button is enabled!"
End Sub
Private Sub ComboBox1_Change()
CheckMandatoryFields
End Sub
Private Sub TextBox1_Change()
CheckMandatoryFields
End Sub
Private Sub TextBox2_Change()
CheckMandatoryFields
End Sub
Private Sub UserForm_Activate()
CheckMandatoryFields
End Sub
If your Buttons and Controls are in a Worksheet, then you need to change UserForm_Activate to Worksheet_Activate. If they are in different worksheets, or some in a Worksheet and others in a UserForm, then you will need to Fully Qualify your references (e.g. Sheet1.Textbox1.Value)
If you are using Form Controls in a Worksheet instead of ActiveX controls, then you can't use the _Change events, and the way you Reference the objects is different:
Sheet1.Shapes("TextBox1").TextFrame2.TextRange.Text 'The value of TextBox1
Sheet1.Shapes("ComboBox1").ControlFormat.Value 'Which Number item in ComboBox1 is selected
Sheet1.Shapes("ComboBox1").ControlFormat.List(n) 'The value of the nth item in ComboBox1
A Form Control button does not have an Enabled property - however, if you have a "Do Nothing" macro, you can bodge it like so:
Sub DoNothing()
'As it says
End Sub
Sub MakeASound()
Beep
End Sub
Sub ToggleButton()
If Sheet1.Shapes("Button 1").OnAction = "Sheet1!DoNothing" Then 'Disable Button 1
Sheet1.Shapes("Button 1").OLEFormat.Object.Font.ColorIndex = 16 'Font colour = Grey
Sheet1.Shapes("Button 1").OnAction = "Sheet1!DoNothing"
Else 'Enable Button 1
Sheet1.Shapes("Button 1").OLEFormat.Object.Font.ColorIndex = 1 'Font colour = Black
Sheet1.Shapes("Button 1").OnAction = "Sheet1!MakeASound"
End If
End Sub
currently i am programming a excel macro. The macro shows a Userform.
In the Userform the User can Select something. After the User has selected something i call Userform.Hide to Hide the Userform and to read the Selection from the Form. After the selection was read i call Unload Userform. Now the Code interacts with the selection. I want to do this in a loop but when the Code trys to show the Userform the second time. I get a exception that the Form is already displayed. I cant understand it, because i called Unload Userform. When i do it in debug mode everthing works as it should.
Userform Code
Private Sub Image1_Click()
SelectCard 1
End Sub
Private Sub Image2_Click()
SelectCard 2
End Sub
Private Sub SelectCard(number As Integer)
SelectedNumber = number
Me.Hide
End Sub
Public Sub CardSelector_Activate(Cards As Cards)
Dim c As card
For Each Key In Cards.CardDictionary.Keys
Set c = Cards.CardDictionary.Items(Key - 1)
If c.value = 1 And c.played Then
Image1.Enabled = False
End If
If c.value = 2 And c.played Then
Image2.Enabled = False
End If
Next Key
number = SelectedNumber
CardSelector.Show
End Sub
Code in the ClassModule i call this in a loop
Sub Costum(Spalte As Integer, Zeile As Integer, SpalteBeginn As Integer, Cards As Cards, CardsOpponent As Cards)
CardSelector.CardSelector_Activate Cards
Dim c As card
Dim number As Integer
number = CardSelector.SelectedNumber
Set c = Cards.CardDictionary.Items(CardSelector.SelectedNumber - 1)
SetCardAsPlaced c, Zeile, Spalte, SpalteBeginn
Unload CardSelector
End Sub
Can someone help me here ?
I am not sure if I fully understand your issue, but this is how I invoke a form using VBA. This is assuming you have a Cancel and OK button:
In the form:
Option Explicit
Private m_ResultCode As VbMsgBoxResult
Private Sub btnCancel_Click()
Call CloseWithResult(vbCancel)
End Sub
Private Sub btnOK_Click()
' Store form control values to member variables here. Then ...
Call CloseWithResult(vbOK)
End Sub
Private Sub CloseWithResult(Value As VbMsgBoxResult)
m_ResultCode = Value
Me.Hide
End Sub
Public Function ShowMe(Optional bNewLayerOptions As Boolean = True) As VbMsgBoxResult
' Set Default to Cancel
m_ResultCode = vbCancel
' Execution will pause here until the form is Closed or Unloaded
Call Me.Show(vbModal)
' Return Result
ShowMe = m_ResultCode
End Function
Then, to call it (please note that frmLayers is my own VBA form object - you would use yours):
Dim dlgLayers As New frmLayers
If (dlgLayers.ShowMe(False) = vbOK) Then
' Proceeed
End If
Does this help you with your issue? I am sorry if I have misunderstood, and I will remove my answer if needed.
Things like xxxxx_Activate etc. are event handlers called by the framework. So, for example, there is an event for activate and an event for initialize. You don't normally have to directly call these yourself if you set your code up correctly. See https://support.microsoft.com/en-us/kb/138819.
I have a textbox on a userform. It is the only textbox on the form. There are three labels and two buttons in addition to this textbox. Basically, I want the focus to remain on this textbox under all scenarios, other than the moment that one of the buttons would be clicked, but then I want the focus to come right back to the text box. Both buttons have "TakeFocusOnClick" and "TabStop" set to False. I was having problems with getting the focus set to the textbox, which is why I changed these two settings.
Once I changed these settings, the Enter key in the textbox stopped having any effect. I have events written for _AfterUpdate and _KeyPress for the textbox, but they don't fire. As you can see in the code, I have commented out the lines to set the focus to this textbox. Since it is now the only object that can take focus, these lines are not needed (theoretically). When I allowed the other objects to take focus, these lines weren't having any effect (focus was switching to the buttons despite these SetFocus lines).
Here is the code. It is very simple, except that the Enter key isn't triggering the event. Can anyone see why? Thanks.
Private Sub btnDone_Click()
Application.Calculation = xlCalculationAutomatic
formMath.Hide
'Clear statistics
Range("attempts").Value = 0
Range("correct").Value = 0
Sheet5.Range("A2:W500").ClearContents
End Sub
Private Sub btnSubmit_Click()
recordAnswer
'formMath.txtAnswer.SetFocus
End Sub
Private Sub txtAnswer_AfterUpdate()
recordAnswer
'formMath.txtAnswer.SetFocus
End Sub
Private Sub txtAnswer_KeyPress(ByVal KeyAscii As MSForms.ReturnInteger)
If KeyAscii = 13 Then
recordAnswer
End If
End Sub
Private Sub UserForm_Initialize()
'Initialize manual calculation
Application.Calculation = xlCalculationManual
Application.Calculate
'Initialize statistics
Range("attempts").Value = 0
Range("correct").Value = 0
Sheet5.Range("A2:W500").ClearContents
'Initialize first problem
newProblem
End Sub
Sub recordAnswer()
'Update statistics
Dim attempts, correct As Integer
attempts = Range("attempts").Value
correct = Range("correct").Value
Range("results").Offset(attempts, 0).Value = attempts + 1
Range("results").Offset(attempts, 1).Value = lblTopNum.Caption
Range("results").Offset(attempts, 2).Value = lblBotNum.Caption
Range("results").Offset(attempts, 3).Value = lblBop.Caption
Range("results").Offset(attempts, 4).Value = Range("Answer").Value
Range("results").Offset(attempts, 5).Value = txtAnswer.Text
If (Range("Answer").Value = txtAnswer.Text) Then
Range("results").Offset(attempts, 6).Value = 1
Else
Range("results").Offset(attempts, 6).Value = 0
End If
'Update attempts and success
Range("attempts").Value = attempts + 1
Range("correct").Value = correct + 1
newProblem
End Sub
Sub newProblem()
Application.Calculate
formMath.lblTopNum.Caption = Range("TopNum").Value
formMath.lblBotNum.Caption = Range("BotNum").Value
formMath.lblBop.Caption = Range("ProbType").Value
formMath.txtAnswer.Value = ""
'formMath.txtAnswer.SetFocus
End Sub
To start off
You can either in the design mode, set the TabIndex property of the Textbox to 0 or you can set the focus on the textbox in the UserForm_Initialize()
Private Sub UserForm_Initialize()
TextBox1.SetFocus
End Sub
Similarly after any operation that you perform, simply call the TextBox1.SetFocus to revert to the textbox.
Option Explicit
Private Sub UserForm_Initialize()
TextBox1.SetFocus
End Sub
Private Sub CommandButton1_Click()
MsgBox "Hello from Button 1"
TextBox1.SetFocus
End Sub
Private Sub CommandButton2_Click()
MsgBox "Hello from Button 2"
TextBox1.SetFocus
End Sub
Let me know if this is not what you want?
I found a way to accomplish this. In the code above I took out the _KeyPress and _AfterUpdate events and replaced them with:
Private Sub txtAnswer_KeyDown(ByVal KeyCode As MSForms.ReturnInteger, ByVal Shift As Integer)
Select Case KeyCode
Case 13: recordAnswer
End Select
End Sub
Not sure why the other methods didn't work, but this does.
Also not sure why simply setting the focus directly didn't work. I suspect that the focus was being set, but then something else was happening subsequently that was changing the focus off of the textbox. Just a guess.
Thanks for the help. I appreciate it.