Combobox null in if statement - ms-access

I am trying to code an if statement where if a certain combobox is null, then it runs a certain part of code if it has data in it then it runs another. I wrote up this:
Private Sub ProjectAddSetDateAutoBtn_Click()
If ProjectAddAllDueDateAutoCmBx = Null Then
'Code1
Msgbox("ComboBox Is Null")
Else
'Code2
Msgbox("ComboBox Has Data")
End If
End Sub
I leave the combobox with no data, and then it doesn't run the code in the first part of the if or the code in the 2nd part of it either! If I enter data into the box, it runs the 2nd part of the if statement perfectly. There are no errors, I am quite stumped on this. Do ComboBoxes have their own "Null"? Is there a problem with this if statement?

Nothing is ever equal to Null, not even another Null.
Use IsNull() to check whether the combo box is Null.
'If ProjectAddAllDueDateAutoCmBx = Null Then
If IsNull(ProjectAddAllDueDateAutoCmBx) = True Then

I would suggest
If IsNull(ProjectAddAllDueDateAutoCmBx.Value) Then
It correctly checks for Null (IsNull instead of = Null), and it explicitly checks the value of the combo box.
(In most cases -- depending on the context -- just using the name of the control yields the value, but it doesn't hurt to be explicit.)

You cannot use a = Null comparison to get the results you want because Null propagates. To see this in action, try:
? Null = Null
in the Immediate Window and you'll see that Null is returned. Use the IsNull function, which will return true or false as you would expect.
Private Sub ProjectAddSetDateAutoBtn_Click()
If IsNull(ProjectAddAllDueDateAutoCmBx) Then
'Code1
Msgbox("ComboBox Is Null")
Else
'Code2
Msgbox("ComboBox Has Data")
End If
End Sub

While the accepted answer is totally correct, I use a different approach:
If HasValue(ProjectAddAllDueDateAutoCmBx) Then
where the HasValue function is:
Public Function HasValue(v As Variant) As Boolean
If Trim(v & "") <> "" Then
HasValue = True
Else
HasValue = False
End If
End Function
This has the advantage of treating NULL and "" (or any pure whitespace) values the same, which is many times what you want with MSAccess controls. For example entering a value in a null-valued textbox and removing it again with backspace will result in a ""-value, not NULL. From a user-perspective this is mostly meant to be the same.
[The (v & "")-part is just a trick to force conversion to a string.]

the equivalent of null in VB is Nothing so your check wants to be:
If ProjectAddAllDueDateAutoCmBx Is Nothing Then
....
it hope helps.

Related

IIF statement with null value and multiple condition

I'm getting a problem with one of my expression in my report. It always gives me #Error and I think I know why but don't know how to set my expression.
Here's my expression :
=IIF(Fields!CMMTTEXT.Value.Contains("*Return*") AND Fields!SOPTYPE.Value = "INVOICE", "*** See return ***", "")
The Fields CMMTTEXT can be null sometimes and I'm getting an error on all of my rows except the one that has data in the CMMTTEXT field.
So I need a isnothing but I've tried couple ways of doing it but doens't seem to work
=IIF(IsNothing(Fields!CMMTTEXT.Value.Contains("*Return*")) AND Fields!SOPTYPE.Value = "INVOICE", "*** See return ***", "")
also this that I've seen on this forum :
=IIF(IsNothing(Fields!CMMTTEXT.Value) OR Fields!CMMTTEXT.Value.Contains("*Return*") AND Fields!SOPTYPE.Value = "INVOICE", "*** See return ***", "")
I have no idea at this point.
Thanks for the help!
The Contains function doesn't work with NULL values. Once it throws an error, the IsNothing function subsequently can't evaluate the results. Separating these out using the OR operator also doesn't work because it tries to evaluate both conditions even when the first one was true.
One way to work around this is to first check for NULL values and replace them with an empty string. Then use the Contains function on the results of this expression:
=IF(IsNothing(Fields!CMMTTEXT.Value), "", Fields!CMMTTEXT.Value).Contains("*Return*")

How to display number values with commas in form

In my Access query, I have the query using a VBA function to figure the value that goes in the query field.
In the form, if the stringval textbox has a value, then I want to compute it, but if not, it should remain empty (null).
Function GetValue(stringval, numval)
Dim result
stringval= stringval & ""
result= IIf(stringval<> "", numval* 1.5, Null)
GetValue = Int(result)
End Function
Now, I have a form that uses this query, and on the form is a textbox that displays the query value. I want the value to be formatted with commas in the numbers for easy reading. Everything I've tried so far does not show any commas.
I've tried:
used Standard for the Format > Formatfor the textbox (in properties)
putting #,###.### in the textbox Format value
putting #,##0.0## in the textbox Format value
changing Data > Text Format but it only gives me Plain Text and Rich Text - no option for numbers.
returning a double from the function
Note: if I don't use a custom VBA function, and write the formula directly into the query, then it does display commas. But when I move the formula into the function then the commas are lost.
What do I do?
[update]
I tried Gustav's solutions and since they didn't work for me, I added those as items to my "what I've tried" list above.
Also, if I look at the query in datasheet view, the number values sort alphabetically instead of by the size of the value. When I used the forumulae directly in the query instead of using functions, it sorted by the value of the number. I hope this is a clue.
Numbers carries no format. A format is applied when displayed only.
But be sure to return a Double if not Null:
Function GetValue(stringval, numval)
Dim result
If stringval & "" <> "" Then
result = Int(CDbl(numval) * 1.5)
Else
result = Null
End If
GetValue = result
End Function
Then apply your Format to the textbox
#,##0.0##
Or force a formatted string to be returned:
If stringval & "" <> "" Then
result = Format(Int(CDbl(numval) * 1.5), "#,##0.0##")
Else
result = Null
End If
and skip formatting of the textbox.
The solution is this: the function has to be declared as a double.
That allows the query's datasheet view to know it is displaying numbers - and so you can set the field's format to Standard for the comma to display. This also allows the form to know it has a number and it will display the comma there, too. I knew it had to do with double, but didn't realize before that the function needed to be declared as such.
Function GetValue(stringval, numval) as double '<----THIS!!!!
Dim result
If stringval & "" <> "" Then
result = numval * 1.5
Else
result = 0 `<--can't return null here; use nz function in control source for textbox
End If
GetValue = int(result) 'to remove decimals
End Function
The problem I was having was in some of my functions I need to return double or null, because I wanted textboxes to remain blank if they contained no data. Now, at least I know how to make the numbers generated by functions to display commas.
And here is how to deal with the fact that you can't return null as the value of a double. The function is originally from here.
Put this function in a module so it is public, and then in the control source for the textbox, instead of just putting the field value, put Zn(fieldvalue). This works like a charm (although using functions in the control source seems to have a delay on the form display). This way you can keep the underlying value as a double and still get commas to display in both the form and the query whilst keeping the field blank if necessary.
Public Function Zn(pvar)
' Return null if input is zero or ""
If IsNull(pvar) Then
Zn = Null
ElseIf IsNumeric(pvar) Then
If pvar = 0 Then
Zn = Null
Else
Zn = pvar
End If
Else
If Len(pvar) = 0 Then
Zn = Null
Else
Zn = pvar
End If
End If
End Function

Filtering Information in A Report Using VBA-Access - Finding the next avaliable null field

I'm trying to organize information in a report in a certain way
I have 9 fields that will be used to store the label for the information
and another 9 fields that store the actual value of the information.
Whenever a field is full, I want it to place the information in the next available field. So that there will be no blank fields in between information.
The issue is that when trying to run this code which triggers two functions, it is not updating the report I referenced to in the two functions, nor is it pulling information from SpecSheetQuery, and I can't figure out why. My guess is that I'm not referencing the information correctly. I also have to figure out how to run this code individually on each record.
Private Sub Detail_Format(Cancel As Integer, FormatCount As Integer)
Servings = DLookup("[servings]", "SpecSheetQuery")
Calories = DLookup("[calories]", "SpecSheetQuery")
If Not IsEmpty(Servings) Then
OpenSlot ("Servings")
OpenFact (Servings)
End If
If Not IsEmpty(Calories) Then
OpenSlot ("Calories")
OpenFact (Calories)
End If
End Sub
OpenSlot function, puts title/label of information into field1 ( which is a field on the report) on the first null/empty field. so that no space is left blank.
Option Compare Database
Option Explicit
Public Function OpenSlot(Slot As String)
Debug.Print Reports!SpecSheet!field1.Value
If Reports!SpecSheet!field1.Value = Null Then
Debug.Print "Slot1"
Slot = Reports!SpecSheet!field1.Value
Debug.Print Reports!SpecSheet!field1.Value
ElseIf Reports!SpecSheet!field2.Value = Null Then
Reports!SpecSheet!field2.Value = Slot
End If
End Function
OpenFact function, puts fact into nut1 ( which is a field on the report) on the first null/empty field. so that no space is left blank.
Public Function OpenFact(fact As String)
If Reports!SpecSheet!nut1.Value = Null Then
Reports!SpecSheet!nut1.Value = fact
Debug.Print Reports!SpecSheet!nut1.Value
ElseIf Reports!SpecSheet!nut2.Value = Null Then
Reports!SpecSheet!nut2.Value = fact
End If
End Function
I'm trying to store this information into this report.
Any help would be greatly appreciated.

Access Vba - To find null and blank values

I am trying to find the blank values and null values in a table. I am using Asc to assign the values of the table to a variable and then based on their ASCII values differentiating null and blank. But I am getting "runtime error 94: Invalid use of null" when the code tries to read the ASCII value of a null field.
When I have to deal with return values that can be either Null or zero-length string, I use a function that converts ZLS to Null:
Public Function varZLStoNull(varInput As Variant) As Variant
If Len(varInput) = 0 Then
varZLStoNull = Null
Else
varZLStoNull = varInput
End If
End Function
This takes advantage of the fact that the VBA Len() function treats a Null and a ZLS exactly the same so that you don't have to handle each case individually.
However, remember that if you use this in a WHERE clause, you'll be losing performance because it can't use the indexes. Thus, in a WHERE clause, you'd test for IS NULL or =""
SELECT MyField
FROM MyTable
WHERE MyField Is Null Or MyField = ""
That will be much more efficient. The varZLSToNull function is most useful when you're appending processed data to a field that has ZLS Allowed set to NO (as it should).
Another thing you should consider is changing your field so that it disallows ZLS, then running a query (using the WHERE clause above without the Is Null) to replace all the ZLS's with Nulls.
Of course, that assumes that your data is not distinguishing between Null and ZLS as meaning two different things (Null meaning "we haven't recorded any value here" and ZLS meaning "we have recorded an empty value here").
You can try the following user-defined function to test the table value:
Public Function text_test(str_in as Variant) As Long
' given input str_in, return -2 if input is Null,
' -1 if input is zero-length string; otherwise return 0
' use function Nz to test if input is Null and return -2,
' otherwise check non-null value with Len
' and return -1 if it is a 0-length string,
' otherwise return 0 for anything else
text_test = IIf(Nz([str_in], "null") = "null", -2, _
IIf(Len(str_in) = 0, -1, 0))
End Function
In the immediate window run a test with different inputs:
?text_test("fred");text_test("");text_test(Null);text_test(9);text_test(False)
Should return:
0 -1 -2 0 0
Note that you cannot use str_in as string in the function declaration since this will cause the same error you refer to in your question.
I think you should be using IsNull() to decide if a value is null.
https://web.archive.org/web/1/http://articles.techrepublic%2ecom%2ecom/5100-10878_11-5034252.html
encapsulate your code inside a if statement and compare the string value to vbNullString like this:
If (Not (<string> = vbNullString) Then
if the string is NOT null execute your original code
if it is null add an Else block to execute what you need to do if the value is null
Yeah, it's an old thread, big deal...
This is the most concise way to test a value for Null and zero-length that I've seen:
FinalValue = IIf(Not Len(Nz(Value, "")) = 0, Value, Null)
How it might perform compared to David Fenton's excellent Function above, I do not know. I do know that the one-liner I present here and David's function do almost exactly the same thing. I suspect the one-liner might perform a bit better than a call out to a Function. On the other hand it makes use of an inclusive If, so it may in fact be slower. Who knows?
I use it in Class modules, mainly. For example, when creating a record with a DAO Recordset:
With rst
.AddNew
!JobCardID = IIf(Not m_JobCardID = 0, m_JobCardID, Null)
!ConstructionProjectID = IIf(Not m_ConstructionProjectID = 0, m_ConstructionProjectID, Null)
!MajorDisciplineID = IIf(Not m_MajorDisciplineID = 0, m_MajorDisciplineID, Null)
!ActivityDescriptorID = IIf(Not m_ActivityDescriptorID = 0, m_ActivityDescriptorID, Null)
!ActivityStatus = IIf(Not Len(Nz(m_ActivityStatus, "")) = 0, m_ActivityStatus, Null
'etc...
End With
In the above code, ActivityStatus is the relevant String.
Note: I never design a database with fields allowing zero-length strings. Repeat: NEVER.

How can you check for null in a VBA DAO record set?

I have an optional field in a database that I'm pulling out using a DAO Record Set. I need to check whether or not the field is set before I concatenate it with other fields. So far I have the following code snippet which I've tried with both Is and = (that's the obviously wrong syntax [[Is | =]]) to no avail. It appears that if I use = it will not correctly compare with Null and if I use Is then it complains that it's not comparing with an Object.
While Not rs.EOF
If rs.Fields("MiddleInitial") [[Is | =]] Null Then thisMiddleInitial = "" Else thisMiddleInitial = rs.Fields("MiddleInitial")
If prettyName(myLastName, myFirstName, myMiddleInitial) = prettyName(rs.Fields("LastName"), rs.Fields("FirstName"), thisMiddleInitial) Then
MsgBox "Yay!"
End If
rs.MoveNext
Wend
If there's a simpler way to do this I'm totally open to it. prettyName takes 3 Strings as parameters and initially I was just trying to pass rs.Fields("MiddleName") directly but it threw up at a Null value. I'd prefer to do something more direct like that but this is the best I could come up with.
How about:
IsNull(rs.Fields("MiddleInitial").Value)
You could also have a look at this article which has some explanation about Null values in Access VBA apps and how to handle them.
For the example you show, Nz would work:
thisMiddleInitial = Nz(rs!MiddleInitial,"")
Or simply concatenating the string with an empty string:
thisMiddleInitial = rs!MiddleInitial & ""
Your question has been answered by Remou, seems to me, but it occurs to me that you may just be trying to get proper concatenation of the name fields. In that case, you could use Mid() and Null propagation in VBA to get the result.
I don't use separate middle initial fields, so my usual name concatenation formula is:
Mid(("12" + LastName) & (", " + FirstName), 3)
The "12" string at the beginning is going to be tossed away if LastName is Not Null and ignored if it is null, because the + concatenation operator propagates Nulls.
To extend this to include middle intials would look like this:
Mid(("12" + LastName) & (", " + FirstName) & (" " + MiddleInitial), 3)
Assuming your UDF is not doing some kind of complicated cleanup of nicknames/abbreviations/etc., this could replace it entirely, seems to me.
If rst.Fields("MiddleInitial").Value = "Null" Then
This works for me. I use MS SQL Database.
I think the NoMatch option might work in this situation:
If rs.NoMatch = True Then
I prefer using the below to account for both Null and Empty string values. It's a good check to use you have forms collecting values from users.
If Trim(rs.Fields("MiddleInitial") & "") = "" then