Question: How do I prompt a user for a password without displaying the value they enter?
Answer: While you can use a field object's No Echo property to hide its value, this doesn't provide much visual feedback to the user. In our experience, it's more effective to create a second form that accepts a password from your users, but displays asterisks instead of the values they enter.
The basic process requires a form with two field objects:
- The first accepts the user's password, but doesn't display it.
- The second is a calculated field that displays a number of asterisks matching the length of the user's current password value.
When you combine this with a bit of visual sleight of hand, you end up with a form that does precisely what you expect it to. This tutorial shows how to create this form and how to integrate it into your existing application. It contains the following sections:
Note: Due to the number of steps involved, this tutorial assumes you already know how to add code to event handlers and have a basic familiarity of ObjectPAL. You don't need to be an expert, but you should be able to change object properties and understand instructions like "add the following code to the button's pushButton() event." If you've never done this before, you may wish to work through our Button Tutorial before tackling this one or you may wish to start with the sample files available in our Download area.
Creating the basic Password form
This section shows how to create the Password form.
Create a new Paradox form and then place four objects:
- A text object to serve as the label for the final product.
- A field object to accept the user's password.
- An OK button for the user to accept the validation process.
- A Cancel button for the user to, well, cancel the process.
When finished, your form should look something like this:

Select the field object, change the following properties as outlined, and then Apply your changes:
| Tab | Property | Setting |
| General | Name | fldPassword |
| General | Display Type | Edit (or Unlabelled) |
Now that your field object is an unlabelled field object, you need change additional properties to help the final appearance of the form:
| Tab | Property | Setting |
| Font | Font | Courier New |
| Font | Font Size | 10 |
| Text | Word wrap | Unchecked |
| Design | Size to Fit | Unchecked |
If you like, you can widen fldPassword to accept additional characters.
Now, copy fldPassword to the ClipBoard by selecting it (if it's not already selected). Click the page background and then paste a copy of fldPassword onto the form. Rename the copy to fldAsterisk.
Right-click fldAsterisk, choose Define Field, click the Calculated checkbox, and then enter the following formula:
fill( "*", size( fldPassword.Value ) )
Choose OK.
Save your form as password.fsl.
At this point, it's a good idea to preview your form to get an idea of how the final process will work and to notice certain behaviors that will need additional attention as we continue. To illustrate:
Run your form by pressing F8.
Notice that focus moves to fldPassword.
Type xyzzy and then press Tab.
Notice that the asterisks do not appear until focus moves to another object. This happens because Paradox, by default, does not recalculate calculated fields until focus leaves fields they depend on. You'll modify this behavior in the next section.
Press F8 to return to Design mode.
Making the Password form "work"
So far, you've laid the foundation for the Password form and seen at least one issue that needs to be addressed. In this section, you'll:
Address the asterisk issue demonstrated while previewing the form by adding ObjectPAL code to override Paradox's default behavior.
Add additional code to make the form work as dialog box.
Move the field objects to complete the visual effect we alluded to.
The following steps deal with each consideration.
To address the asterisk issue, select fldPassword and then add the following code to its keyPhysical event:
method keyPhysical(var eventInfo KeyEvent)
doDefault
fldAsterisk.postAction( dataRecalc )
endMethod
This tells Paradox to recalculate fldAsterisk each time the user presses a key while fldPassword has focus.
Next, it's time to complete the visual trick. The requires careful formatting of the two field objects. To do this:
Set fldPassword's Run Time | No Echo property to True placing a checkmark in the property sheet.
Set fldAsterisk's Run Time | Tab Stop property to False by removing its checkmark.
Select both field objects and then choose the following commands:
- Format | Alignment | Align Left
- Format | Alignment | Align Top
- Format | Size | Maximum Width
- Format | Size | Maximum Height
- Format | Group
Note: You grouped the objects together for two reasons. It makes them easier to move as a unit and it works around a quirk in the Paradox visual designer. When you stack multiple objects, the selection handles tend to disappear. This is a known behavior and is best handled by placing stacks of objects in a container, such as a group.
To make the OK button functional, add the following code to its pushButton() event:
doDefault
formReturn( TRUE )
The purpose of this code will become clear as you complete the tutorial.)
Add the following code to your Cancel button's pushButton() event:
doDefault
formReturn( FALSE )
Important: Save your form.
At this point, your form should look similar to this:

There are additional things we could do and we'll examine a few of these in a few moments. However, at this point, it's important to note that with a few objects, six lines of code, and a bit of visual sleight of hand, we've created a basic form that prompts the user for a password and displays asterisks as they enter it.
Next, you'll see how to use your Password form to actually obtain a password from the user.
Using the Password form
To use the password form, you need to use ObjectPAL to:
Open and display the form
Wait for the user to enter a password
Obtain the user's password and compare it to the actual password
Display errors for incorrect passwords or process authorized activities
We'll demonstrate one way to do these tasks by creating a simple script:
Make sure your Password form is saved and then close it.
Create a new script.
Add the following code to the run() event:
method run(var eventInfo Event)
var
frmPassword Form
strPassword String
endVar
const
AUTHPASS = "xyzzy"
endConst
if not frmPassword.open( "password" ) then
errorShow( "Can't Get Password",
"Use [>>] for details..." )
return
endIf
if frmPassword.wait() then
strPassword = frmPassword.fldPassword.Value
if strPassword <> AUTHPASS then
msgStop( "Sorry",
"You didn't enter the correct password." )
else
msgStop( "Congratulations",
"You've entered the secret word." )
endIf
endIf
try
frmPassword.close()
onFail
; do nothing; it's already closed
endTry
endMethod
Save your script as PassTest.ssl and then run it.
There are many ways to incorporate passwords into your Paradox applications; this example is merely a starting place. While we'll leave many to your imagination, there are a few things to you can do to make your Password form more effective and some issues you should think about. These are discussed in the next sections.
Making the Password form more effective
Even though you have a working Password form, there are a few changes that would make it more effective. For example, you might change the form's Window Style properties to make it look like a dialog box or you might add keyboard shortcuts. Let's do these and add some code to make sure that the buttons are the only ways to exit and close the form:
Note: While the next steps aren't strictly necessary and contain suggestions matching our personal coding practises, we strongly recommend them as a starting point. Feel free to implement these ideas differently if you already use different standards. However, please do so after considering why we've chosen our approaches.
Open your Password form in a Design window.
Right-click the Design window's title bar and then set the following properties:
| Setting | Value |
| Title: | Enter Password |
| Window Style: | Dialog Box |
| Frame Properties: | Dialog Frame |
| Title bar Properties: | Uncheck Maximize button and Minimize button. |
Rename the OK button to btnAccept and the Cancel button to btnCancel.
Edit your form's menuAction() event as follows:
method menuAction(var eventInfo MenuEvent)
if eventInfo.isPreFilter() then
;// This code executes for each object on the form
else
;// This code executes only for the form
if eventInfo.id() = menuControlClose then
eventInfo.setErrorCode( userError )
btnCancel.pushButton()
endIf
endIf
endMethod
Modify your form's keyPhysical() event as follows:
method keyPhysical(var eventInfo KeyEvent)
if eventInfo.isPreFilter() then
disableDefault
switch
case eventInfo.vCharCode() = VK_RETURN :
btnAccept.pushButton()
case eventInfo.vCharCode() = VK_ESCAPE :
btnCancel.pushButton()
otherwise : enableDefault
endSwitch
else
;// This code executes only for the form
endIf
endMethod
Make any additional cosmetic changes you want to make Password appear as professionaly as possible.
Save your form.
In the last series of steps, you've:
Converted your Password form to a dialog box. Be aware that once you do this, you have to use the Edit option of the File | Open | Form dialog to change the design of the form.
Made certain that consistent exit points are used to close your Password form. (For more information, please see Providing Consistent Exits from your Forms.)
Added keyboard shortcuts for accepting and cancelling the dialog.
Additional notes and considerations
As we mentioned earlier, there are a host of enhancements and other considerations to think about. Following is a brief list of things to ponder. (Because this tutorial is fairly long already, we will not be discussing them in detail here. Future articles may provide additional details, if we receive enough feedback requesting them.)
This tutorial only prompts for a password; however, it contains the information needed to add a UserName prompt to the dialog. We'll leave this as a homework exercise.
You can easily extend the calling code to count log-in attempts. We'll also leave this as a homework exercise, but it involves adding a counter variable and a loop to the calling code.
If you plan to use your Password form from multiple locations in your Paradox application, consider creating a library with a getPassword() routine. In the long run, this makes it easier to maintain and reuse your work.
We used Courier New as the font for the field objects because it is a monospaced font. Had we used a proportionally spaced font (e.g. Arial or Times New Roman), the visual effect would not work. Try it out to see what we mean, though use care to not save your changes.
The code presented for calling the password form is not secure. Someone interested in learning the actual password could open your script (or calling form) in a binary editor and locate the actual password quite easily. Delivering the source file helps, but not much.
Storing the password in protected tables provides more security, however, there are ways to break Paradox table passwords.
For best results, consider encrypting the real password in your source. (For one technique, please see Implementing Playfair Encryption.)
We're sure you'll think of a number of other things as you work with your Password form. Hopefully, though, this tutorial has given you an idea of the sorts of things you can create with Paradox and an idea of how ObjectPAL can help make Paradox much easier to use than you might have expected. In the end, you're only limited by your creativity and imagination.