[AccessD] Event sink order

John W. Colby jwcolby at colbyconsulting.com
Thu Aug 4 11:01:04 CDT 2005


When a control's events are sunk in more than one class, the order that
events are sunk (which class gets control first) is determined by the order
that the classes are initialized.  In other words, if Class1 and Class2 sink
events for ComboZ, the class that is initialized LAST gets control FIRST -
IN A2K AND LATER!!!. In A97 the situation is reversed.

In order to test this, I created two classes, Class1 and Class2:

'**************************************************
Option Compare Database
Option Explicit

Const cstrClassName As String = "Class1"

Dim WithEvents mcbo As ComboBox
Const cstrEvProc As String = "[Event Procedure]"

Function Init(cbo As ComboBox)
    Set mcbo = cbo
    mcbo.AfterUpdate = cstrEvProc
End Function

Private Sub mcbo_AfterUpdate()
    debug.print cstrClassName
End Sub

'**************************************************
Option Compare Database
Option Explicit

Const cstrClassName As String = "Class2"

Dim WithEvents mcbo As ComboBox
Const cstrEvProc As String = "[Event Procedure]"

Function Init(cbo As ComboBox)
    Set mcbo = cbo
    mcbo.AfterUpdate = cstrEvProc
End Function

Private Sub mcbo_AfterUpdate()
    debug.print cstrClassName
End Sub

'**************************************************

Notice the only difference between the classes is the string constant that
"names" the class.

I then created a form that uses these two classes:

'**************************************************
Option Compare Database
Option Explicit
Dim fcls1 As Class1
Dim fcls2 As Class2
Private Sub Form_Open(Cancel As Integer)
    Set fcls1 = New Class1
    Set fcls2 = New Class2
    fcls2.Init Combo0
    fcls1.Init Combo0
End Sub

Private Sub Combo0_AfterUpdate()
    debug.print "Form event sink"
End Sub

'**************************************************

The form has a single combo box with a simple list of things to select.

In order to test whether it is the SET statement or the actual
initialization of the class, I SET the classes in order, but INITed the
classes in reverse order.

Opening the form and selecting an item in the combo caused:

Form event sink
Class2
Class1

To be printed in the debug window.

This is in Access2K.  Likewise in XP.

In A97 the OPPOSITE was true, i.e. the class initialized FIRST gets control
first.

I finally ran into a case where the order does matter.  In a client's
application, they use a set of 5 check boxes to denote different attributes
of a claim.  There are dependencies between the checkboxes, dictated by a
set of rules.

Private WithEvents mchkWorkComp As CheckBox
Private WithEvents mchkAutoRelated As CheckBox
Private WithEvents mchkAccident As CheckBox
Private WithEvents mchkIllness As CheckBox
Private WithEvents mchkMaternity As CheckBox

The rules go something like:

A Automobile claim IS an Accident, but NOT an illness.
An Illness is NOT an Accident or auto related 
A maternity claim is not an accident and vice versa

etc. etc.  

I built a class using withevents that sink the click event for these check
boxes, then use the following to "get it right"

Private Sub mchkWorkComp_Click()
    mchkMaternity.Value = False
    RaiseEvent Finished
End Sub
Private Sub mchkAutoRelated_Click()
    mchkAccident.Value = True
    mchkIllness.Value = False
    mchkMaternity.Value = False
    RaiseEvent Finished
End Sub
Private Sub mchkAccident_Click()
    mchkIllness.Value = False
    mchkMaternity.Value = False
    RaiseEvent Finished
End Sub
Private Sub mchkIllness_Click()
    mchkAccident.Value = False
    mchkAutoRelated.Value = False
    RaiseEvent Finished
End Sub
Private Sub mchkMaternity_Click()
    mchkAccident.Value = False
    mchkIllness.Value = True
    mchkAutoRelated.Value = False
    mchkWorkComp.Value = False
    RaiseEvent Finished
End Sub

The problem now is that the Benefit effective date of the policy depends on
just TWO of these check boxes, chkAccident and chkIllness.  I have an entire
class that performs the calculations required to calc the Benefit effective
date, and that class has to sink these two check boxes (accident / illness).
Thus I need the main class that manipulates ALL of the check boxes to gain
control first, get the various check boxes in the desired states, then my
class that calculates the dates needs to get control after the "check box
states" have been determined.

Given that requirement, and what we now know about sink order, I need to
make sure that the main check box class is initialized LAST, so that it gets
control FIRST.  

The order that events are sunk between classes can make a difference in how
you application operates.  If you get it wrong, you may have unintended
consequences that are difficult to track down.  

John W. Colby
www.ColbyConsulting.com 

Contribute your unused CPU cycles to a good cause:
http://folding.stanford.edu/





More information about the AccessD mailing list