LightBox Class - More with embedded PNG's
A LightBox dialog technique in VFP
You may or may not have heard of the LightBox Dialog UI Effect. It is one of the current effects making the rounds, and has been described as the "Interaction Design Technique of the Year" on this page where design awards for 2008 were announced -
http://www.useit.com/alertbox/application-design.html (scroll down midway)
Well this effect can very easily be implemented in VFP with a simple image and a PNG with a mask.
You may recall that I showed the usage of PNG's with transparent masks to enhance the GUI in these posts:
http://weblogs.foxite.com/bernardbout/archive/2006/09/11/2436.aspx
http://weblogs.foxite.com/bernardbout/archive/2006/11/04/2798.aspx
and showed a technique for embedding images in these:
http://weblogs.foxite.com/bernardbout/archive/2007/02/18/3320.aspx
http://weblogs.foxite.com/bernardbout/archive/2007/07/15/4366.aspx
At the end of this post will be a class where you can get this LightBox effect in your VFP applications. It uses a masked PNG that is "Embedded" into the class so no external files are needed.
The class is just dropped on a form or into a container on the form and when needed, the Display() method is called passing a couple of parameters. As described elsewhere, the LightBox is useful to focus a user's attention on a modal messagebox. Therefore the Display() method needs to be called just before displaying the modal form and after to remove it.
The sample form provided shows how this can be called using the VFP MessageBox() but you can very easily substitute that for your own modal messagebox form as per your own design. That is beyond the scope of this post, which is just about the LightBox class.
Here the class is added to the Form as well as a container in the Form in the VFP IDE.

This is the code from a method called from the Exit button:
LPARAMETERS tcMsg
LOCAL lRet as Boolean
ThisForm.lightbox1.Display(.F.,.T.)
IF MESSAGEBOX(tcMsg,292,"Are you sure?",0) = 7
lRet = .F.
ELSE
lRet = .T.
ENDIF
ThisForm.lightbox1.Display()
RETURN lRet
The Display() method is called with 2 optional parameters. The First parameter is the Object over which the LightBox will be overlaid, and if .F. , the parent object is assumed. The second is to switch the class on or off.
ThisForm.lightbox1.Display(.F.,.T.)
means Show the LightBox for the form(default)
This shows the form running. The Lightboxes are not visible.

Here the Container Lightbox is toggled on

And finally the LightBox class in action on the form. See how it emphasises the messagebox?

This effect makes the messagebox stand out and being modal, the user is forced to read the message and act on it. As I said earlier, it is not too difficult to use your own custom messagebox. All that is required is to insert a call to the LightBox.Display() just before showing the Messagebox and immediately after, to hide it.
Enjoy.
19/08/2008 Update
Thanks to Cyril & Cesar for finding this. The class had deleted records hence the image mask was not loading. Download has been updated. Also PNG's changed to BMP because of VFP handling of PNG's. Please download latest version below.
19/08/2008 2nd Update
This tip is from Cesar (http://weblogs.foxite.com/vfpimaging)
With this tip you can implement the LightBox class with very few changes as it wraps your original MessageBox() calls.
Where ever you want to use the LightBox class along with a messagebox() - example is for the Exit button:click()
#DEFINE MESSAGEBOX LightBoxMsgBox
IF MESSAGEBOX("Are you sure you want to quit",292,"Are you sure?",0) = 7
RETURN
ELSE
ThisForm.Release
ENDIF
Then, create a small PRG that will wrap the original MESSAGEBOX command Call it LIGHTBOXMSGBOX.PRG
LPARAMETERS tcMessage, tnType, tcTitleBarText, tnTimeOut
LOCAL loForm as Form
loForm = _Screen.ActiveForm
loForm.lightbox1.Display(.F.,.T.)
LOCAL llReturn as Boolean
llReturn = MESSAGEBOX(tcMessage, tnType, tcTitleBarText, tnTimeout)
loForm.lightbox1.Display()
RETURN llReturn
This way, you wont need to change any code in your forms, just add the line below
#DEFINE MESSAGEBOX LightBoxMsgBox
in a header ".H" file, linked to your forms class. Great tip Cesar.
20/08/2008
Updated zip file to v1.03. New property maskfile to use an external maskfile.
This is because only VFP9Sp2 handles PNG's properly when using the PICTUREVAL property. If the property is left empty then it will load the internal PNG - (for Sp2)
Also corrected version of Cesar's sample code.
[snip]
MESSAGEBOX() command returns integer values, not boolean, so the function will stay better this way:
LPARAMETERS tcMessage, tnType, tcTitleBarText, tnTimeOut
* Some few tweaks in the parameters, in order to make MESSAGEBOX()
* work as desired, for the case when some parameters are missing
tnType = EVL(tnType, 0)
IF VARTYPE(tcTitleBarText) <> "C"
tcTitleBarText = "Microsoft Visual FoxPro"
ENDIF
IF NOT VARTYPE(tnTimeOut) $ "NI"
tnTimeOut = 0
ENDIF
* Find the LightBox object and activate it
IF TYPE("_Screen.ActiveForm.Name") <> "C"
* Could not locate an active form
RETURN
ENDIF
LOCAL loForm as Form
loForm = _Screen.ActiveForm
loForm.lightbox1.Display(.F.,.T.)
* Call the original MESSAGEBOX() command
LOCAL liReturn as Integer
liReturn = MESSAGEBOX(tcMessage, tnType, tcTitleBarText, tnTimeout)
* Deactivate the LightBox
loForm.lightbox1.Display()
RETURN liReturn
This function probably still needs some tweaks, specially at the part for locating the LightBox object.
[endsnip]