Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations gkittelson on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

can't compile, object method wants assginment?

Status
Not open for further replies.

1DMF

Programmer
Jan 18, 2005
8,795
GB
Hi,

Why is this
Code:
Forms!Check_Case.Form!Nav_Subform.Form.oFileWatcher.FileIOCompletion(dwErrorCode, dwNumberofBytes, lpOverlapped, oUser)
erroring , with
Compile error : expected =

the method FileIOCompletion of the oFileWatcher object doesn't return a value (it's a sub not a function), and it isn't a setter so doesn't take an assignment

if I check the object
Code:
msgbox not(Forms!Check_Case.Form!Nav_Subform.Form.oFileWatcher is nothing)
I get True - ie the object exists and is set.

What is access talking about?

"In complete darkness we are all the same, it is only our knowledge and wisdom that separates us, don't let your eyes deceive you."

"If a shortcut was meant to be easy, it wouldn't be a shortcut, it would be the way!"

Free Dance Music Downloads
 
Typically in VBA if you have () it expects an assignment. Try without the ()s
Code:
Forms!Check_Case.Form!Nav_Subform.Form.oFileWatcher.FileIOCompletion dwErrorCode, dwNumberofBytes, lpOverlapped, oUser

Duane
Hook'D on Access
MS Access MVP
 
Or use Call:
Call Forms!Check_Case.Form!Nav_Subform.Form.oFileWatcher.FileIOCompletion(dwErrorCode, dwNumberofBytes, lpOverlapped, oUser)

Hope This Helps, PH.
FAQ219-2884
FAQ181-2886
 
neither work!

If I leave out the parentheses it errors with
only user-defined types in public modules can be coerced to or from a variant or passed to late-bound functions

it highlights lpOverlapped , but this is in a standard public module as follows
Code:
Option Compare Database
Option Explicit

' UDT
Public Type OVERLAPPED
        Internal As Long
        InternalHigh As Long
        Offset As Long
        OffsetHigh As Long
        hEvent As Long
End Type
Public Sub FileIOCompletionRoutine(ByVal dwErrorCode As Long, ByVal dwNumberofBytes As Long, ByRef lpOverlapped As OVERLAPPED)
    
    If Not Forms!Check_Case.Form!Nav_Subform.Form.oFileWatcher Is Nothing Then
        [highlight #FCE94F]Forms!Check_Case.Form!Nav_Subform.Form.oFileWatcher.FileIOCompletion dwErrorCode, dwNumberofBytes, [highlight #EF2929]lpOverlapped[/highlight], oUser[/highlight]
    End If
    
End Sub

If I use Call and keep the parentheses it errors with
compile error: expected . or (

and highlights the bang after the Forms collection
Code:
Call Forms[highlight #EF2929]![/highlight]Check_Case.Form!Nav_Subform.Form.oFileWatcher.FileIOCompletion(dwErrorCode, dwNumberofBytes, lpOverlapped, oUser)

If I change the bangs to periods I get the first error again.

"In complete darkness we are all the same, it is only our knowledge and wisdom that separates us, don't let your eyes deceive you."

"If a shortcut was meant to be easy, it wouldn't be a shortcut, it would be the way!"

Free Dance Music Downloads
 
How is dimmed lpOverlapped in the calling module ?

Hope This Helps, PH.
FAQ219-2884
FAQ181-2886
 
It's not dimmed it's a private attribute and is used byref in the following class method

Code:
            ' set up the async call
            ReadAsync hFolder, cBuffer(0), 1024, False, nFilter, nReturned, [highlight #FCE94F]OL[/highlight], AddressOf FileIOCompletionRoutine  ' 0&

I've given up, if I put the oFileWatcher object on the main form ...
Code:
Public WithEvents oFileWatcher As clsFileWatcher

and then in the same routine where I am having problems use ...
Code:
        Call Form_Check_Case.oFileWatcher.FileIOCompletion(dwErrorCode, dwNumberofBytes, lpOverlapped, oUser)

It works fine, but as soon as I try to tidy up the process and put the object on the subfrom where technically it should be it refuses to work.

So I've gone back to putting it on the main form and instead of referencing the main form object from the subform I've created a public sub on the main form which the subform calls and setz up the watcher object that way.

Access doesn't want to play ball when the object is public on the subform, works fine when it is on the main form.



"In complete darkness we are all the same, it is only our knowledge and wisdom that separates us, don't let your eyes deceive you."

"If a shortcut was meant to be easy, it wouldn't be a shortcut, it would be the way!"

Free Dance Music Downloads
 
for debug purposes I would do something like this. Lets you work piece by piece and know where the error is.
Code:
dim frm as access.form
dim subFrm as access.form
dim ofw as clsFileWatcher
set frm = forms("Check_Case")
set subFrm = frm.Nav_SubFrom.Form
set ofw = subFrm.oFileWatcher
debug.print dwErrorCode
debug.print dwNumberOfBytes
debug.print lpOverlapped.Internal
'if that looks good then try
ofw.fileIOCompletion dwErrorCode, dwNumberofBytes, lpOverlapped, oUser

you never showed the procedure
FileIOCompletion
Do all the parameters and arguments match up? You do not pass oUser in your routine, but then you use it. Is that some kind of global variable?

Code:
Public Sub FileIOCompletionRoutine(ByVal dwErrorCode As Long, ByVal dwNumberofBytes As Long, ByRef lpOverlapped As OVERLAPPED)
    
    If Not Forms!Check_Case.Form!Nav_Subform.Form.oFileWatcher Is Nothing Then
        Forms!Check_Case.Form!Nav_Subform.Form.oFileWatcher.FileIOCompletion dwErrorCode, dwNumberofBytes, lpOverlapped, oUser
    End If
    'where did oUser come from all the others were passed in?
End Sub
 
Hi MajP,

Here is the FileIOCompletion method of the clsFileWatcher class.

Code:
Public Sub FileIOCompletion(ByVal dwErrorCode As Long, ByVal dwNumberofBytes As Long, ByRef lpOverlapped As OVERLAPPED, ByRef oMyUser As clsUser)

    Dim wombat As FILE_NOTIFY_INFORMATION ' the infamous wombat!

    If dwNumberofBytes Then  ' did we get anything?
    
        CopyMemory wombat, cBuffer(0), dwNumberofBytes

        Select Case wombat.Action
        
            Case FILE_ACTION_ADDED

                ' stop watching
                Me.CancelWatcher = True
                    
                ' move dropped email file and raise event
                RaiseEvent FileMoved(Me.MoveFile(oMyUser, Left(CStr(wombat.FileName), wombat.FileNameLength / 2)))

            Case FILE_ACTION_MODIFIED
            Case FILE_ACTION_REMOVED
            Case FILE_ACTION_RENAMED_NEW_NAME
            Case FILE_ACTION_RENAMED_OLD_NAME
            Case Else

        End Select
        
    End If
    
End Sub

You do not pass oUser in your routine, but then you use it. Is that some kind of global variable?

Yes, it is an application wide global object of the current user, I was accessing it directly from within the clsFileWatcher class, but realised this was wrong, and so decided to pass it in as an argument, though I am kind of thinking perhaps it should be an attribute, rather than being passed around byref between the clsFileWatcher methods.

What would you suggest?

FileIOCompletionRoutine is an application procedure in a standard module
FileIOCompletion is a method in the clsFileWatcher class

The FileIOCompletionRoutine is simply a wrapper for the class method due to the fact you cannot use 'AddressOf' for a class method, this is all kicked of by the clsFileWatcher method FileWatch

Code:
Public Sub FileWatch()

On Error GoTo err_FileWatch

    Dim nFilter As Long
    Dim nReturned As Long
    Dim WaitResult As Long
    Dim ByteCount As Long
    
    Me.CancelWatcher = False
    
    If sFolder <> "" And sTarget <> "" And lContactID > 0 And sEmailType <> "" And sFileExtType <> "" Then

        ' Create our own event, and stick it in the OVERLAPPED structure so that
        ' we can link it to our asynch ReadDirectoryChangesW
        hEvent = CreateEvent(0&, False, False, "vbReadAsyncEvent")
        OL.hEvent = hEvent
        
        ' Get handle to nominated folder
        hFolder = CreateFile(sFolder, FILE_LIST_DIRECTORY, FILE_SHARE_READ + FILE_SHARE_DELETE + FILE_SHARE_WRITE, 0&, OPEN_EXISTING, FILE_FLAG_BACKUP_SEMANTICS + FILE_FLAG_OVERLAPPED, 0)
        
        ' Filter the type of file events we want to monitor
        nFilter = FILE_NOTIFY_CHANGE_FILE_NAME + FILE_NOTIFY_CHANGE_LAST_WRITE + FILE_NOTIFY_CHANGE_CREATION
        
        ' Keep looping until user cancels
        Do While Not (Me.CancelWatcher) And Not (WaitResult = WAIT_IO_COMPLETION)
        
            ' set up the async call
            [highlight #FCE94F]ReadAsync hFolder, cBuffer(0), 1024, False, nFilter, nReturned, OL, [highlight #D3D7CF]AddressOf FileIOCompletionRoutine[/highlight] ' 0&[/highlight]
            
            Do While Not (Me.CancelWatcher) And Not (WaitResult = WAIT_IO_COMPLETION)
            
                ' Wait for event or timeout to occur
                WaitResult = WaitForSingleObjectEx(hEvent, 100, True)
                DoEvents ' Yield to OS
                
            Loop
        Loop
    Else
        sError = "Folder watch details missing, watch aborted"
    End If
    

exit_FileWatch:

    ' cancel filewatch
    Me.CancelWatcher = True
    
    ' Clean up as we go
    CloseHandle hEvent
    CloseHandle OL.hEvent
    CloseHandle hFolder
    OL.hEvent = 0
    OL.Internal = 0
    OL.InternalHigh = 0
    OL.Offset = 0
    OL.OffsetHigh = 0
    hFolder = 0
    Exit Sub
    
err_FileWatch:
    sError = "Error in FileWatch : " & Err.Description
    Resume exit_FileWatch
    
End Sub

"In complete darkness we are all the same, it is only our knowledge and wisdom that separates us, don't let your eyes deceive you."

"If a shortcut was meant to be easy, it wouldn't be a shortcut, it would be the way!"

Free Dance Music Downloads
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top