Re: Managing the flow of forms...

From: Fred Boer (Fredboer1_at_NOyahooSPAM.com)
Date: 04/26/04


Date: Mon, 26 Apr 2004 14:57:56 -0400

Dear Allen, Jeff, Albert...

Well, first of all, apologies: I asked you to keep an eye on this thread and
then left it rather longer than I expected. I knew it would take me some
time to get to this... but I didn't expect the death of my hard disk to
intervene. (What a pain rebuilding your computer is...even if you have your
data backed up! :( )

Well, I've tried a few things, and what I am going with for now is the
following:

One main modal form, which serves as what the user sees when no forms are
open. Closing this form quits application.
All other forms are opened through a menu bar which is visible at all times.
All forms have standard windows controls.
Any form can be opened at any time.
Some forms are opened from command buttons on "parent" forms. In these cases
the "child" forms are opened with OpenArgs (filtered to one record, and read
only).

I have a really simple application, and this seems to work, although I have
yet to do any serious testing..

I am wondering about whether I actually want the main modal form, since
minimized windows are hidden behind it. These windows can still be re-opened
via the menu, but users might forget they are there, although I don't
*think* that matters...

Thanks!
Fred

"Fred Boer" <fredboer1@NOyahooSPAM.com> wrote in message
news:%23SdQENIJEHA.2572@TK2MSFTNGP12.phx.gbl...
> Dear Allen:
>
> Thanks for your suggestions! Although I am experimenting with modal forms
as
> per Jeff and Albert, I really am interested in the "flexible" approach you
> are suggesting. Unfortunately, (since this is a "lunch hour and after the
> kids are in bed" hobby), I probably won't be able to do anything until the
> beginning of next week.. (the kids never seem to go to bed on the weekend
> and for some reason my wife wants me to have lunch with *her* not
Access...
> <g>).
>
> I am certain I will have questions/need further help, so, if you would be
so
> kind, could you watch this thread over the next while? I would appreciate
> it!
>
> Many thanks!
>
> Fred
>
> "Allen Browne" <AllenBrowne@SeeSig.Invalid> wrote in message
> news:4080d002$0$16593$5a62ac22@freenews.iinet.net.au...
> > Well, you, Jeff and Albert all use mostly modal forms, so I'm the odd
one
> > out here. Just checked the last 4 applications I wrote, and there *no*
> bound
> > modal forms - just a couple of unbound dialogs.
> >
> > Since you expressed an interest in trying that approach, here are some
> > ideas. The underlying philosophy is to rely on the events instead of
> > thinking of sequences of things. In practice, it is incredibly simple.
We
> > have a couple of default forms set up, with the properties set to the
> > generic functions, so it actually takes us *no* extra time to design it
> this
> > way.
> >
> > 1. Subform with no record in main form
> > ============================
> > Jeff raised this. Dead easy. Set the foreign key's Required property.
> > Then (so that the user gets a message instantly rather than after
filling
> in
> > the subform), we set the subform's BeforeInsert property to:
> > =RequireParent([Form])
> >
> > Public Function RequireParent(frmMe As Form) As Integer
> > If frmMe.Parent.NewRecord Then
> > MsgBox "Enter main form record first", "Insert Canceled..."
> > DoCmd.CancelEvent
> > RequireParent = True
> > End If
> > End If
> >
> > Relying on the engine and the event, the problem never arises.
> >
> >
> > 2. Keeping something open
> > ====================
> > Set the On Close property all forms (except the switchboard) to:
> > =Keep1Open([Form])
> > and all reports to:
> > =Keep1Open([Report])
> >
> > Public Function Keep1Open(objMe As Object)
> > Dim sName As String 'Name of the object being
closed.
> > Dim lngObjType As Long 'acForm or acReport
> > Dim bFound As Boolean 'Flag not to open the
switchboard.
> > Dim frm As Form 'an open form.
> > Dim rpt As Report 'an open report.
> >
> > If TypeOf objMe Is Form Then
> > lngObjType = acForm
> > ElseIf TypeOf objMe Is Report Then
> > lngObjType = acReport
> > End If
> >
> > 'Any other visible forms?
> > For Each frm In Forms
> > If frm.Visible Then
> > If frm.Name <> sName Or lngObjType <> acForm Then
> > bFound = True
> > Exit For
> > End If
> > End If
> > Next
> >
> > 'Any other visible reports?
> > If Not bFound Then
> > For Each rpt In Reports
> > If rpt.Visible Then
> > If rpt.Name <> sName Or lngObjType <> acReport Then
> > bFound = True
> > Exit For
> > End If
> > End If
> > Next
> > End If
> >
> > 'If none found, open the switchboard.
> > If Not bFound Then
> > DoCmd.OpenForm "frmSwitchboard"
> > End If
> > End Function
> > (Note: trap error 2046.)
> >
> >
> > 3. Dependencies
> > ============
> > In the AfterUpdate and AfterDelConfirm events of every bound form, call
> > another generic procedure which will handle the concurrency issues. For
> > example, if the user double-clicks a combo and adds an item to the
lookup
> > list, this routine will requery any combos on other forms that have that
> > table as RowSource.
> >
> > When you are developing your forms, you probably don't know what other
> parts
> > of the interface will rely on them, but that doesn't matter. Just call
the
> > generic routine. Then, when all the forms are in place (including the
> > interface the reports if that uses combos to offer filtering options),
you
> > can examine the dependencies and write the body of this routine. It ends
> up
> > being one large Select Case to handle each form, but we find the
> maintenance
> > is easiest if all dependencies are in the one place, and it allows you
to
> > develop forms willy-nilly and sort out the dependencies at the end.
> >
> > Public Function NotifyCombos(frmSource As Form, Optional vStatus =
> > acDeleteOK)
> > Select Case frmSource.Name
> > Case "frmMyLookup"
> > If IsLoaded("MyOtherForm") Then
> > Forms!MyOtherForm!cboMyLookup.Requery
> > End If
> > ...
> >
> > 4. Concurrency
> > ===========
> > You do need to be aware of what else might be open at the same time if
> both
> > could be dirty, but we do not force a save in a form's Deactivate event
> > since that would defeat the whole point of going somewhere else to
create
> or
> > lookup data while entering/editing.
> >
> > If you plan to execute an Update or Delete query, it's a good idea to
> > consider the implication for forms that may be open, and close them or
at
> > least ensure they are not Dirty. That's just good practice anyway.
> >
> > If you issue an OpenForm/OpenReport and the thing is already open,
Access
> > does not give it focus (so it does not appear) and any WhereCondition or
> > OpenArgs is not applied. We use a little wrapper function that closes it
> if
> > it is already open, defaults to preview mode, handles error 2501 if the
> > report does not open, etc. Since the report is meaningless without a
> > description of its filter, our wrapper accepts that as well, and it is
> > handled and cleared by another generic function called in the Format
event
> > of the report's Header.
> >
> > Public Function OpenTheReport(strDoc As String,
> > Optional lngMode As Long = acViewPreview,
> > Optional strWhere As String,
> > Optional strDescrip As String) As Boolean
> >
> > If IsLoaded(strDoc, acReport) Then
> > DoCmd.Close acReport, strDoc
> > End If
> > gstrTitleInHeader = strDescrip
> > DoCmd.OpenReport strDoc, lngMode, , strWhere
> > OpenTheReport = True
> > End Function
> >
> >
> > Hopefully that's enough to let you experiment with the idea of just
> relying
> > on the events.
> >
> > --
> > Allen Browne - Microsoft MVP. Perth, Western Australia.
> > Tips for Access users - http://allenbrowne.com/tips.html
> > Reply to group, rather than allenbrowne at mvps dot org.
>
>