Excel VBA: Highlight textbox value after error occurs - excel

I am trying to highlight entered value in TextBox. TextBox value is representing date value in date forma DD-MM-YYYY. I wrote some code to validate if inserted date is ok (in example 31 of April).
Hightlight itself is not a problem, however I want to do this right after an error occurs. So when I insert 31-04-2014, I should get the message "You have inserted wrong date" and the date value should hightlighted. For now it shows me message, highlights value and focus is set to another CommandButton
So far I made something like this:
Private Sub data_faktury_AfterUpdate()
Dim dzien As Byte, miesiac As Byte
Dim rok As Integer
On Error GoTo blad:
dzien = Mid(data_faktury.Value, 1, 2)
miesiac = Mid(data_faktury.Value, 4, 2)
rok = Right(data_faktury.Value, 4)
Call spr_date(dzien, miesiac, rok)
Exit Sub
blad:
If Err.Number = 13 Then
If data_faktury <> "" Then
If Len(data_faktury) < 10 Then: MsgBox ("Źle wpisana data faktury.")
End If
End If
End Sub
And code for 2nd procedure:
Sub zle()
MsgBox ("Wybrałeś zły dzień")
With Faktura.data_faktury
.SetFocus
.SelStart = 0
.SelLength = Len(.Text)
End With
End Sub

This is a bit long for a comment so here goes. The basic principle is to use the exit event and cancel when necessary. To prevent this being fired when you close the form, you need to use a flag variable - example userform code:
Private bSkipEvents As Boolean
Private Sub TextBox1_Exit(ByVal Cancel As MSForms.ReturnBoolean)
If bSkipEvents Then Exit Sub
With TextBox1
If Not IsValidDate(.Text) Then
Cancel = True
MsgBox "Invalid date"
.SelStart = 0
.SelLength = Len(.Text)
End If
End With
End Sub
Private Sub UserForm_QueryClose(Cancel As Integer, CloseMode As Integer)
bSkipEvents = True
End Sub

Related

VBA Multiple Textboxes Validation control

Dears,
I am preparing a simple userform to let a teacher to enter each student’s name and height in a class. There are two textboxes (textbox_name and textbox_height) and one “add to record” command button. I tried to make some validation control to prevent empty string to be entered. My validation control is in case textbox is empty, when the click the “add to record” button, the corresponding empty textbox turns pink; and when both textboxes are empty, both textboxes should turn pink, however only the first textbox turns pink in my below codes. Can you tell me why and how to correct it? Thanks.
Private Sub Cmd_addtorecord_Click()
If TextBox_Name = "" Then
TextBox_Name.BackColor = rgbPink
Exit Sub
End If
If TextBox_height = "" Then
TextBox_height.BackColor = rgbPink
Exit Sub
End If
'....
End sub
You can do it like this:
Private Sub Cmd_addtorecord_Click()
'ensure required fields have content
If FlagEmpty(Array(TextBox_Name, TextBox_height)) > 0 Then
MsgBox "One or more required values are missing", vbExclamation
Exit Sub
End If
'....
End Sub
'check required textboxes for content, and flag if empty
' return number of empty textboxes
Function FlagEmpty(arrControls) As Long
Dim i As Long, numEmpty As Long, clr As Long
For i = LBound(arrControls) To UBound(arrControls)
With arrControls(i)
clr = IIf(Len(Trim(.Value)) > 0, vbWhite, rgbPink)
.BackColor = clr
If clr = rngpink Then numEmpty = numEmpty + 1
End With
Loop
FlagEmpty = numEmpty
End Function
You're Exiting the sub before you get to the second textbox. Change your code to something like this:
Private Sub Cmd_addtorecord_Click()
If TextBox_Name = "" or TextBox_height = "" Then
If TextBox_Name = "" Then
TextBox_Name.BackColor = rgbPink
End If
If TextBox_height = "" Then
TextBox_height.BackColor = rgbPink
End If
Exit Sub
End If
'....
End sub

How to exit from the loop when user clicks X button on userform?

I have vba code below to edit every row one by one on userform interface:
Private Sub CommandButton1_Click()
Dim MyRange As Range
Dim cell As Range
Set MyRange = Range("A2", Range("A2").End(xlDown))
For Each cell In MyRange
cell.Select
'Build form
MyForm.Title.Caption = cell.Offset(0, 2)
If cell.Offset(0, 2) = 1 Then
MyForm.Checked.Value = True
Else
MyForm.Checked.Value = False
End If
'Show form
MyForm.Show
Next cell
End Sub
I have thousand of rows and I need to give user a some break!
I want this process to pause if user clicks X button, but I couldn't find a way to exit from the loop.
My userform code is like below:
Private Sub Checked_Click()
If MyForm.Checked.Value = True Then
ActiveCell.Offset(0, 1).Value = 1
Else
ActiveCell.Offset(0, 1).Value = ""
End If
End Sub
Private Sub DoneButton_Click()
ActiveCell.Offset(0, 2).Value = 1
Unload MyForm
End Sub
Private Sub UserForm_QueryClose(Cancel As Integer, CloseMode As Integer)
If CloseMode = vbFormControlMenu Then
MsgBox "paused"
End If
End Sub
What I'm trying to accomplish?
I need to stop for each loop at first block of code when users click X button to close the userform. But I don't know how to listen if UserForm_QueryClose called to exit loop from first block of code.
Sadly I don't think this is possible, given vba doesn't support multi-threading.
If you really insist on asking the user whether to pause, it would be better to simply ask an If conditional during the run-time.
eg.
For i = 1 to myRange.Cells.Count
' your code here...
If i = myRange.Cells.Count / 2 Then
If MsgBox("Continue to the for loop?", vbYesNo) = vbNo Then
UnLoad MyForm
Exit For
End If
End If
Next i
You need to add DoEvents which will check for a user interaction. However, simply closing the form will not stop the code from running so you will need to add another controller.
For example
Option Explicit
Private stopCode As Boolean
Private Sub UserForm_Click()
Dim i As Long
stopCode = False
For i = 1 To 1000000
Debug.Print i
DoEvents
If stopCode = True Then Exit For
Next
End Sub
Private Sub UserForm_QueryClose(Cancel As Integer, CloseMode As Integer)
If MsgBox("Do you want to stop", vbQuestion + vbYesNo) <> vbYes Then Cancel = True
stopCode = True
End Sub
When the user closes the form they will be asked if they want to stop the code. If they say yes it closes the form but the stopCode 'controller' also makes sure the running code is stopped.

Excel VBA: Highlight textbox value after error occurs - similar

All,
I have a simple userform with two textboxes. I'm attempting to trap an error and send the user back to TextBox1 if the entry is > 1,000. I found code on this site which gets close under the same Title as above.
The code below traps the error and highlights the number >1,000 entered in Textbox1 (without an error message box). However, if I "uncomment" and enter the
MsgBox ("Value is Greater than 1,000")
after the Cancel = True the error will trap, the msg box displays, but the number greater than 1,000 will not highlight.
I've pulled most of what remains of my hair trying to see why this doesn't work and the example I'm following does. Help!!
Thanks
Stan
Private SkipIT As Boolean
'------------------------------------------------------
Private Sub TextBox1_BeforeUpdate(ByVal Cancel As MSForms.ReturnBoolean)
If SkipIT Then Exit Sub
With Me.TextBox1
If Val(Me.TextBox1.Value) > 1000 Then
Cancel = True
'MsgBox ("Value is Greater than 1,000") 'Will highlight if this line is commented, but no error message box
.SetFocus
.SelStart = 0
.SelLength = Len(.Text)
End If
End With
End Sub
'--------------------------------------------------------------------
Private Sub UserForm_QueryClose(Cancel As Integer, CloseMode As Integer)
SkipIT = True
End Sub

Setting minimum value to a textbox

I am using a userform with multiple textbox. I was wondering if there is a way of forcing the user to input a minimum value or higher before moving to the next textbox.
Thanks a lot,
Assuming one of your textboxes is named TextBox1 you can place this code in your userform:
Option Explicit
Dim blnClosing As Boolean
Private Sub TextBox1_BeforeUpdate(ByVal Cancel As MSForms.ReturnBoolean)
If blnClosing = False Then
Dim iVal As Integer
Dim minVal As Integer
minVal = 10 'Change to your needs
'Test for numeric characters
On Error Resume Next
iVal = CInt(Me.TextBox1.Value)
'If characters are not numeric
If Err.Number = 13 Then
MsgBox "Value must be numeric!", vbCritical, "Incorrect Value"
Me.TextBox1.Text = vbNullString
Cancel = True 'Retain focus on the textbox
Exit Sub
End If
'Reset error handling to normal
On Error GoTo 0
'Check if textbox value is less than the minimum
If Me.TextBox1.Value < minVal Then
MsgBox "Value must be greater than " & minVal & "", vbCritical, "Incorrect Value"
Me.TextBox1.Value = vbNullString
Cancel = True 'Retain focus on the textbox
End If
End If
End Sub
Private Sub UserForm_QueryClose(Cancel As Integer, CloseMode As Integer)
blnClosing = True
End Sub
I took the liberty of checking for a numeric value as well, since you are asking if the value in the textbox appears to be required to be numeric. If that's not the case remove the lines of code from the 'Test for numeric characters comment down to the On ErrorGoTo 0 line.
The global variable blnClosing allows us to skip over the code when the form is closing. If this wasn't included and the user pressed 'X' on the upper right hand corner of the form with invalid data (blank, less than the minimum, or non-numeric) then the messageboxes would show.

Excel Userform Textbox Behavior

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.

Resources