DCount("[ID]", "qryReturnUsersRecords", "[LessonNo] = " & NZ(Forms!frmGetInputData!txtLessonNo,"0"))
Unless [ID] is actually a string that holds a field name itself. But from context, I'm not reading that possibility. DCount builds an SQL string which it executes via something like DoCmd.ExecuteSQL. Then it reads the result and passes that back to you. That is why you need to assure that the arguments are consistent with that goal - SQL generation.
Watch:
DCount("[ID]", "qryReturnUsersRecords", "[LessonNo] = " & NZ(Forms!frmGetInputData!txtLessonNo,"0"))
Parse that out to recognize
Function = DCount
Arg1 = "[ID]"
Arg2 = "qryReturnUsersRecords"
Arg3 = "[LessonNo] = " & NZ(Forms!frmGetInputData!txtLessonNo,"0")
Now take template "SELECT COUNT(" & arg1 & ") FROM (" & arg2 & ") WHERE " & arg3 & ";" - which is because it is DCount.
Do the subsititution, execute it, and trap the result, which will be a single record in a recordset with one field. See how it works?
Oh, make sure that Forms!frmGetInputData!txtLessonNo is text format, too. The substitution won't attempt an automatic CStr() call to convert it.