Mastering FoxPro - (For Version 1.01 - Charles Siegel
Mastering FoxPro - (For Version 1.01 - Charles Siegel
01
Beginners: Create, Edit &
Use Your Own Database
Intermediate Users:
Customize Screens &
Applications to Suit You
Advanced Users: Expand
Your Capabilities
Through Programming
Principal Database Management Operations Using FoxPro
The Change
display
EMPLIST ■ : - ’ . ■
The Browse Fname Lname Address
display
Audrey Levy 318 B. 31 St.
JACK LOVE 3642 TANACH WAY
EDNA CHANG 2701 ADDISON WAY
CHARLOTTE SAGORIN 2203 SHADY LANE
WILLIAM JOHNSON 523 EAST 21 ST.
■WILLIAM B. ■JOHNSON- 11701 ALBEMARL E RD.
NANCY NIXON 1124 GRANT AVE.
JAMES SKINNER 1206 FRANCISCO ST.
Laying Out a Report
The report layout window gives you a simple, visual method of creating a
report form. The window begins with three bands, one for the page header, one
for the page footer, and one for the detail line that is repeated for each record
included in the report. You can add bands for a report title and report sum¬
mary; you can also group data and include bands for each grouping.
The report
layout window
Charles Siegel
SYBEX has attempted throughout this book to distinguish proprietary trademarks from descriptive terms by
following the capitalization style used by the manufacturer.
Every effort has been made to supply complete and accurate information. However, SYBEX assumes no responsi¬
bility for its use, nor for any infringement of the intellectual property rights of third parties which would result
from such use.
Copyright ©1990 SYBEX Inc., 2021 Challenger Drive #100, Alameda, CA 94501. World rights reserved. No
part of this publication may be stored in a retrieval system, transmitted, or reproduced in any way, including but
not limited to photocopy, photograph, magnetic or other record, without the prior agreement and written permis¬
sion of the publisher.
https://archive.org/details/masteringfoxproOOsieg
A CKNOWLEDGMENTS
Introduction xix
APPENDICES
Appendix A Installing FoxPro 513
Appendix B The FoxPro Filer and Desktop Utilities 521
Appendix C Essential Commands and Functions 553
Index 620
XI
Table of Contents _
Introduction xix
Other Features 32
Getting Help 34
Quitting 37
Xll
Appending Data 80
Deleting a Record 99
Reindexing 151
Fields 202
XIV
Replace 325
Selection 407
Analysis 423
APPENDICES
Index 620
'
,
XIX
Introduction
WHAT IS A DATABASE? __
SIMPLE DATABASES
A simple database is organized in pretty much the same way that
data has generally been organized on paper.
A typical file in an old-fashioned office was made up of a collection
of identical forms, each with blank spaces where information was
supposed to be filled in. A typical example would be a list of names
kept on a collection of index cards, each of which was printed to show
you where to fill out the name, the address, the city, the state, the zip
code, and the telephone number. Most data was kept on larger forms
that went into file folders, but the basic principle was the same: a
standard form would be prepr inted to indicate the type of data that
was needed, and there were blank spaces where you had to fill in the
actual data needed on each form.
Simple databases are organized in the same way. All you need to
learn are the new terms that are used to describe them once they have
been computerized:
These are the three basic terms that you will hear repeatedly when¬
ever people are talking about databases. They are summarized in
Figure 1.1, which shows how database terminology would be used to
describe the old-fashioned index-card file.
RELATIONAL DATABASES
Some of the advantages of computerizing data are obvious. A
computer can instantly look up the record you want: for example, if
you are looking for the telephone number of a certain person. It can
print out the data in different forms, saving you the trouble of copy¬
ing it from the list in the form you need: for example, it can print out
a list of names and phone numbers when you want to call people, and
can print out labels when you want to do a mailing. It can instantly
select only certain records from the file: for example, it can list the
names and phone numbers of only the people who live in New York,
or it can print out mailing labels for only the people who live in New
Jersey. It lets you use the data in different orders: for example, you
can effortlessly print out your mailing labels in zip code order and
print out your list of names and phone numbers in alphabetical
order.
In addition to these obvious advantages of computerizing data,
early computer scientists found a more subtle advantage of com¬
puterization. They found that computers made it possible to avoid
repetition.
In the days of the paper office, for example, a typical large business
had dozens of different forms that included the name and address of
each employee. The payroll department used a form with the name,
address, and wages of each employee; the benefits department used a
form with the name, address, and eligibility for benefits of each
employee; the human resources development department used a
form with the name and address and the training courses taken by
each employee; and so on.
This repetition was obviously inefficient. The same name and
address—and, of course, other basic information such as Social Secu¬
rity number and telephone number—had to be filled out over and
over again. If an employee moved, a dozen different people in a
dozen different departments would have to change the address on
a dozen different forms.
Repetition could not be avoided in a paper office, but computer
scientists quickly devised ways to let a business enter the names and
addresses only once and to let each department use those names
and addresses in combination with the specific data that it needed
about wages, benefits, training courses, or whatever.
Early methods that were used for tying all this data together were
very complex and unwieldy. There were hierarchically organized
databases and databases organized as networks that were held
together using pointers, both of which were so complicated that they
could only be understood and used by programmers with training in
database theory. Companies had to have teams of programmers just
to retrieve information or to produce reports.
In 1970, E. F. Codd invented a new way of tying together this sort
of data, which was called the relational database. His idea was to break
down the data into separate files, which could be related using a com¬
mon key field.
In the example we have been looking at, the business would proba¬
bly use an employee number as a key field. Then it could have one
file with each employee’s employee number, name, address, and
other basic data, another file with each employee’s employee number
and wages, another file with each employee’s employee number and
eligibility for benefits, and so on. Basic information such as the name
and address would only have to appear once. Each department
would have a program that used the employee number to relate the
data it needed on wages or benefits to the basic data that everyone
needed.
With relational databases, most of the work of relating the data
was built into the database management program. You did not need
programmers to create pointers to relate one record to another. You
just had to enter the right employee number and wage in one file, and
the database management system would do the work of relating that
record to the record in another file that had the name and address for
that employee number.
Codd analyzed the relational database using mathematical set the¬
ory and discovered ways to break down the data that minimized
repetition. Because they were both powerful and simple to visualize
and to use, relational databases quickly became the preferred method
of handling complex data.
XXlll
Using FoxPro
Getting
Aquainted with FoxPro
Fast Track '***
To make a selection from the menu using a mouse, 8
point at the menu pad that you want and press the mouse but¬
ton to make the menu popup appear. Continue to hold down
the mouse button while dragging to highlight the menu option
you want. Release the mouse button to select that option.
To quit FoxPro, 37
select Quit from the File menu popup, or enter QUIT in the
Command window. Always quit FoxView when you are done
with it to avoid loss of data.
6 MASTERING FOXPRO
CH. 1
INTRODUCING THE
FOXPRO MENU STRUCTURE _
structure. First, of course, you must start the program. If you have
not yet installed FoxPro, see Appendix A for installation instructions
before going on.
1. Make sure you are in the FOXPRO directory that was cre¬
ated when you installed the program.
Figure 1.1: The initial FoxPro screen, with the menu and Command window.
The main menu is at the top of the screen. Most of the screen is
taken up by the FoxPro logo with the copyright notice under it, and
the Command window is near the bottom of the screen. Notice
that the cursor is in the Command window, ready for you to enter a
procedural command. (Unfortunately, the cursor does not appear in
the screen images used in the figures. When it is important to know
where to find the cursor, the text will instruct you where to look.)
The highlighted menu across the top of the screen is called the menu
bar. Each of the words written in the menu bar is called a menu pad, as
in keypad. Think of each pad as a button. As you will see, when you
select one of the menu pads, a menu popup will appear, containing a
group or groups of choices called menu options.
8 MASTERING FOXPRO
CH. 1
When you perform certain operations with FoxPro, you will find
that some of the menu pads that are no longer relevant to what you
are doing will disappear from the menu bar. Sometimes, you will also
find extra pads added to the right of the pads already on the menu
bar. For example, when you are creating mailing labels, a Label pad
will appear, permitting you to access additional options relevant to
working with labels.
When you look through the menu popups, you will see that a
USING A MOUSE
• press the Alt key by itself or the F10 key by itself to move the
cursor to the menu bar. The cursor will land on the System
menu pad initially, but the System menu popup will not
appear. To select the menu pad that you want, use the left
and right arrow keys to move the cursor to that menu pad;
then make the menu popup appear by pressing any of the fol¬
lowing: Enter, the space bar, the up or down arrow key, or
any character key.
After you have made one menu popup appear, you can make others
appear by moving the highlight left or right from one menu pad to
another; however, only one menu popup can appear at a time. It is
sometimes convenient to browse through the menu popups in this way.
Once the menu popup that you want has appeared, you can
a The highlighting of
the letter to press in
choose the menu option from within it in a couple of ways. Either
After you select a menu option, the menu popup will disappear, and
FoxPro will do whatever your selection has told it to do.
10 MASTERING FOXPRO
CH. 1
Bller
alculator
Calendar/[giary
Special Characters
Ascgi Chart
Capture
Pugzle
iipen.
Close
Save
Save as.
Revert
Printer Setup.
Print...
Quit
CH. 1
another name, and Revert lets you cancel the changes that you made
to a file since it was last saved.
As you work with FoxPro—creating database files, indexes, reports,
and mailing labels—you will use these first two groups of menu options
constantly.
The options in the third group let you print, and, finally, the Quit
option lets you leave FoxPro and return to DOS.
Undo ~U
Redo ~R
Cut
Copy ~C
Paste "'V
Clear
Select All ~A
Goto Line...
Find... ~F
Find Again '"G
Replace And Find Again ~E
Replace All
Preferences...
you become an advanced user of the editor, these shortcuts can make
it a very powerful and fast word processor.
The basics of the editor and a couple of the most useful menu fea¬
tures, such as Copy and Paste, are discussed later in this chapter.
Advanced features of the Edit menu are discussed in Chapter 8.
Average..
Count...
Sum...
SCalculate
eport...
abel...
Pack
Reindex
The two options in the first group let you do basic operations on
the entire file. Setup lets you determine how the data in the file will be
displayed. Browse lets you look at and edit data from the entire file.
The next grpup of options lets you perform operations that involve
two separate files: appending the data in one file to another, copying
from one file to another, sorting the records from one file into an¬
other, and totaling the numeric fields from one file into another.
The next group of options lets you work with one file, performing
numeric operations or producing reports or labels.
14 MASTERING FOXPRO
CH. 1
The final group includes two utilities which let you finalize dele¬
tions and repair indexes.
The first option, Do, lets you run a program. The pair of options
below Do let you stop running a program or resume running a pro¬
gram. The options in the following group are useful for debugging.
The options in the final group are utilities. Compile, predictably,
lets you compile a program. Fox View is the application generator
that you will learn about in Chapter 9. FoxDoc is the documentation
generator. FoxGraph lets you access a program to generate graphs of
FoxPro data; this graphics program is not included with the FoxPro
package and must be purchased separately.
CH. 1
Hide
Clear
Move "F7
Size ~F8
Zoom ■'F10
gycle HU
Cofjor. ..
I
Command U£j
ebug
race
lew
The first option, Hide, lets you hide a window and temporarily
suspend use of it. The second option, Clear, clears the contents of a
window. Both of these options will be discussed further later in this
chapter, along with most of the options in the second group, which let
you change the appearance of a window.
The options in the third group let you use special windows: the
Command window (which you have already seen), the Debug and
Trace windows (which are used in programming), and the powerful
View window, discussed in Chapter 7.
Once you have this general overview of it, the FoxPro menu system is
not difficult to understand. It offers so many options it can be confusing,
but once you realize that only some of the options on a few of the popups
are essential to using FoxPro, it becomes easy to understand.
Three of the popups are fundamental. The File popup is essential
for creating and using the files that hold databases, indexes, reports,
mailing labels, and so on. The Database popup is essential for work¬
ing with whole database files, and the Record popup is essential for
working with records and groups of records within files.
GETTING ACQUAINTED WITH FOXPRO 17
INTRODUCING
FOXPRO DIALOG BOXES
S
_
Dialog boxes are As you have seen, many of FoxPro’s menu options are followed by
often called “dia¬ ellipses. If you choose one of these options, you will be presented with
logs” in other books
about FoxPro. For clar¬
a dialog box asking you for more information. Within a dialog box,
ity, however, this book there are a number of different types of controls, which are used for
uses the more precise different purposes. Some of these controls can also contain ellipses:
term “dialogbox.”
choosing one of these controls will take you to another dialog box ask¬
ing you to enter more information.
In this section, you will begin by looking at the different types of
controls within dialog boxes, and then you will learn to use each
of these controls with either a mouse or the keyboard.
CH. 1
sorted. After you choose one option from the popup, the popup
disappears so it does not get in your way, and the name you
chose appears within the control, as DEMO does now.
a In some FoxPro
dialog boxes, only
• text box: The Output rectangle in this dialog box is a text
box. You can type text into it, or you can have FoxPro dis¬
the position of the cursor play text resulting from your menu choices. In this example,
lets you know that you you can either type the name of the hie where you want the
can type text at that
sorted output saved or select the Save As text button within
point.
the text box to choose a hie name, which will then appear
next to (or often below) the text button.
20 MASTERING FOXPRO
CH. 1
Ctrl-Tab moves you from one control to another: generally, Tab moves
the highlight “forward” through the controls, and Ctrl-
Tab moves “backward.” Once you have highlighted the control you
want, you can use the arrow keys to move within it. For example,
you would use the arrow keys to move to the different items in a scrol¬
CH. 1
make the selection with the mouse—and the Window menu popup
will display the Hide All and Show All options instead of its Hide
option. (Similarly, if you hold down Shift when you select the File
menu pad, the popup will include a Close All option.)
SPECIAL WINDOW
CONTROLS FOR MOUSE USERS
The descriptions of windows that you have read so far apply to
both mouse and keyboard users. If you are a mouse user, FoxPro
windows are particularly easy to manipulate, because of the special
controls on their borders.
Figure 1.10 shows the Command window (looking a bit larger
than usual) with the names of all the features that you find in window
borders. The figure also shows the menu popup, for your conven¬
ience when you read the more general discussion of using windows.
close box
CH. 1
• zoom control: Click the zoom control in the upper right cor¬
ner to “zoom” a window—that is, to make it fill the entire
screen. Click the zoom control again to return it to its pre¬
vious size.
• scroll bar: If the display is too long or too wide to fit in the
window, a scroll bar made up of two arrows and a diamond
appears. To move up or down through a file, click the up or
down arrow on the right border of the window. The position
of the diamond, called the thumb, indicates where in the file
the cursor is. The closer the thumb is to the up or down
arrow, the closer the cursor is to the beginning or end of the
file. To move quickly through a file, use the mouse to drag
the thumb. If the display is too wide for the window, a scroll
bar also appears on the bottom border, and is used in the
same way.
CONTROLLING
WINDOWS WITH THE KEYBOARD
If you are using a keyboard, you can control windows by using the
Window menu options, or the hot keys that appear next to some of
the menu options. If you do something frequently enough, you will
learn the hot keys without any effort, and then you will be able to
work just about as quickly as someone with a mouse.
GETTING A CQUAINTED WITH FOXPRO 25
The FoxPro editor is very elegantly designed, and its basic opera¬
tions are very easy to learn.
Most keys are used in the ordinary way—the character keys to
enter text (of course), the Del key to delete the character the cursor is
on, the Backspace key to delete the character to the left of the cursor,
and so on.
The Ins key is used in the conventional way, to toggle back and
forth from insert mode to type-over mode. When you begin typing,
you are in insert mode: anything you type will be inserted to the left
of the character that the cursor is on, and everything after that char¬
acter will be pushed to the right to make room for it. If you press Ins
26 MASTERING FOXPRO
CH. 1
to toggle into type-over mode, anything you type will write over and
replace existing text, character by character. When you are in type-
over mode, the cursor becomes large, a warning that existing text can
be lost.
The cursor movement keys are also used conventionally. The
arrow keys move one character to the left or right or one line up or
down. The Home key moves the cursor to the beginning of the line it
is on, and the End key moves it to the end of the line. PgUp and
PgDn scroll up and down through text a window at a time. Of
course, you might prefer to use the mouse to move through the text.
Remember that the text will always be in a window, so you can use
the scrolling techniques mentioned in the previous section.
All these ways of using the editor are very common. The uncom¬
mon thing about the FoxPro editor is the way it uses the cursor move¬
ment keys in combination with Ctrl and Shift. These key movements
are summarized in Table 1.1. In general, Ctrl magnifies movements,
and Shift marks text as you move.
a Ctrl is not used with
the up and down
Looking at the table, you can see that holding down Ctrl when you
move the cursor makes it go further. For example, the right and left
arrow keys, as PgUp and
PgDn serve the same
arrow keys by themselves move the cursor one character to the right
purpose. or left; Ctrl plus those keys makes it move a whole word to the right or
left. Home and End by themselves move the cursor to the beginning
or end of a line; Ctrl-Home and Ctrl-End move it to the beginning or
end of the document.
In addition, since Backspace by itself deletes a character, Ctrl-
Backspace deletes a word. However, Ctrl has no special effect with Del.
If you decide after
Holding down Shift when you move the cursor marks text, mak¬
releasing the Shift
key to continue to mark
ing it appear in reverse video; this is sometimes called selecting text.
text, you can simply hold You can use Shift in combination with the arrow keys, Home, End,
down the Shift key again PgUp, or PgDn to mark text. You can also use Shift in combination
and move the cursor
further. Be sure you hold
with the extended cursor movements (those using the Ctrl key). For
down Shift first, though, example, since Ctrl-End moves the cursor to the end of the docu¬
or else moving the cursor ment, Shift-Ctrl-End moves it to the end of the document and marks
will unmark all the text
all the text along the way.
you have already marked.
You can also mark text using a mouse. Position the pointer where
you want the marking to begin, hold down the mouse button, and
drag to mark the text; when you have marked all the text you want,
release the mouse button. To unmark text, place the pointer any¬
where outside the marked area but inside the window, and click.
GETTING ACQUAINTED WITH FOXPRO 27
Key Effect
Any of these keys or key combinations can be used with Shift to mark
text as you move the cursor.
Apart from these simple mouse operations, there are other shortcuts
for marking text with the mouse, shown in Table 1.2.
Pressing the space After you have marked it, you can perform operations on the
bar or any character entire block of marked text. One of the notable consequences of this is
might also delete all
that if you press Del or Backspace, the editor will delete all the
marked text. If you mark
text by mistake, be sure marked text. The easy way to delete all the text from the cursor to
to unmark it by pressing the end of the line, then, is to press Shift-End to mark the text to the
a cursor movement key
end of the line and then press Backspace to delete it. The easy way to
or by using the mouse
before you resume typ¬ delete all the text from the cursor to the end of the document, simi¬
ing. Fortunately, if you larly, is to press Shift-Ctrl-End to mark the text and then press Back¬
do delete text by mistake,
space to delete it.
you can recover it by
selecting Undo, discussed
To unmark text, press any cursor movement key (Home, End,
below. PgUp, PgDn, or one of the arrow keys) without holding down the
Table 1.2: Shortcuts for Marking Text with the Mouse
Purpose Method
Shift key. The cursor will move and the marking of the text will
disappear.
popup. That’s all there is to it. (As you get used to using FoxPro, you
will naturally begin using the Ctrl shortcut keys to do these things,
speeding up the operation even more.)
One other pair of features of the Edit popup that you will find very
handy in circumstances that are not always possible to avoid are the
Undo and Redo features. If you make an error, such as deleting a
large block of text by mistake, select Undo from the Edit menu
popup. This will undo the last editing action you made, restoring the
text to the state it was in before you made the error.
You can continue to choose Undo to undo all the past editing
actions that you made during the current work session, one at a time,
starting from the most recent and working back to the first.
If you use Undo by mistake, then you can select Redo from the
Edit menu popup to recover the editing action that you undid most
recendy.
You have now learned enough about the FoxPro editor to use it for
most practical purposes. You will be using this editor throughout
FoxPro for entering data, entering commands, writing programs,
writing text files, and so on.
WORKING WITH
THE COMMAND WINDOW
a Remember that the
Command window
_
As you have seen, the Command window lets you enter the sort of
procedural commands used in earlier dBASE compatible programs
behaves a bit differently
from most FoxPro win¬
rather than having you work through the menu system. You also
dows. You cannot close it know that the procedural commands are generated in the Command
by pressing Esc. In addi¬ window when you do use the menu system.
tion, it is not added to the
This sort of procedural command was the only thing available in
list of active windows at
the bottom of the Win¬ the days of the dot prompt, but there are still reasons to use it in this
dow menu popup when it era of the pop-up menu and mouse.
is hidden. To unhide it,
It is sometimes easier to enter commands than to make selections
you simply reselect it
from where it is always
from the menu system—particularly when you are performing a
listed: in the Window repetitive task—since you can edit and reenter commands that you
menu’s third group of already used. A list of all the commands you have entered or gener¬
options.
ated by using menus remains available in the Command window
throughout your work session. You can use the up arrow key (or the
mouse) to move the cursor to earlier commands, even to those that
30 MASTERING FOXPRO
CH. 1
have scrolled beyond the top of the window. Once you have found
the command that you want, just press Enter to reuse it as is. At that
point the command will be executed and the cursor will return to the
bottom of the list, where a copy of that command will be added. If
you want to use a variation on the command, you can edit it first,
using any of the editing techniques you just learned, and then press
Enter to execute it and add it to the list in its revised form.
Of course, if you ever want to do any programming, you must also
learn these commands, since a program is, in large part, a list of these
commands.
For these reasons, this book will begin by using the menu system to
enter commands but will also mention the procedural commands
that are generated in the Command window, so that you can learn
both. For now, you should try entering a couple of procedural com¬
mands in the Command window, just to get an idea of how it works.
You may find the FoxPro command RUN very helpful in your
work: this is a utility that lets you use any DOS command directly
from within FoxPro. In the example, you will use the command
RUN DIR
to get a DOS directory from within FoxPro. Of course, you can also
use RUN with other DOS commands—for example,
RUN FORMAT A:
to format the disk in the A drive. You will also use the FoxPro com¬
mand CLEAR, which, like Clear from the Window menu, clears the
screen or the contents of the current output window. You will notice,
when you enter these commands, that they do not apply to the Com¬
mand window itself.
While it runs, Fox¬ 2. Type RUN DIR and press Enter. FoxPro will display a DOS
Pro sometimes
directory similar to the one illustrated in Figure 1.11. (Of
creates and uses tempo¬
rary files whose names course, your directory will not be exactly like the illustration.)
are made up of random
3. Type CLEAR and press Enter to clear the screen.
numbers and letters and
which have no extension;
you can see one in the
illustration of the direc¬
| System File Edit 1Database Record 1 Window
tory listing. Do not delete PROWORDS FXD 5440 11:10a
10-20-89
these files while you are in FX2W0RDS FXD 1039 3-01-87 9 : 06p
FXDPRT FXD 1860 9-29-89 11:57a
FoxPro. Most will be FOXVIEW 000 57856 9-07-89 2 : 47p
FOXVIEW 001 46336 9-07-89 2 : 48p
deleted automatically FOXVIEW 002 57088 9-07-89 2 : 49p
FOXVIEW 003 41984 9-07-89 2 : 48p
when you quit FoxPro; if
0104-3844 2362 12-04-90 1 : 08a
any are left, you may FOXVIEW COM 38877 12-04-90 2:13a
FOXVIEW MSG 22528 9-07-89 1 :57p
delete them while FoxPro DEMO DBF 1171 5-27-88 10:12a
FOXVINST PRG 2745 9-21-89 6 : 44a
is not running. FVBRAND COM 11568 5-27-88 1:38p
FVDEMO BAT 973 6-17-88 4: 30p
FOXVIEW BAK 1458 12-04-90 2 : 12a
FOXVIEW CFG 1454 12-04-90 2:13a
TEMPLCOD <DIR> 12-04-90 2:15a
FOXHELP FPT 851127 11-09-89 1 : 22p
FOXHELP DBF 18589 11-09-89 1 : 22p
FOXGEN COM 64968 5-27-88 9:33a
FOXBIND EXE 39840 3-09-89 2 : 23p
FOXBIND RSC 23993 8-30-88 3 : 56p
54 File(s) 1588544 bytes f ree
DIR *.EXE
Rather than typing the entire command
Notice that the command, in its edited form, is added to the end of
the list of commands in the window and that the new DOS directory
appears, as in Figure 1.12.
System File Edit Database Record Program Window
Volume in drive C has no label
Directory of C:\FOXPRO
You can imagine how valuable the ability to edit and reuse com¬
mands can be if, for example, you are copying a large number of files
with slighdy different names. There are many cases where it is easier
to use and reuse commands than to repeat the same series of menu
choices over and over again.
OTHER FEATURES _
That takes care of all the major features of the FoxPro interface,
but there are a few smaller ones that you should know about.
CH. 1
The preceding informadon on the Esc key and on “talk” tells you
what FoxPro does by default. As you will see in Chapter 7, it is pos¬
sible to disable either of these features by using the View window or
by entering the command
or
SET ESCAPE ON
or
SET TALK ON
In general, though, you should not disable these features unless you
are a programmer setting up foolproof systems for end users. When
you are using FoxPro yourself, it is always best to have escape on and
talk on, as they are by default.
Figure 1.13: The beginning of the list of topics in the Help window.
Once the list of topics is displayed, you can also type the first letter
or the first few letters of a command, and FoxPro will immediately
move the cursor to the first topic beginning with those letters. You
will be doing this in the next exercise.
One remarkable feature of FoxPro is that you can use the editor to
copy commands out of the Help window and then paste them into the
Command window. This feature is particularly useful when you are
working with a complex command whose exact syntax is difficult to
remember. You should try a simple example now to see how it
works. In the following exercise, you will copy the CLEAR command
out of the Help window and use it to clear the screen again.
1. Select the System menu pad and select Help from the menu
popup. A list of topics—commands, functions, and operators—
will appear. Notice that the command HELP was generated in
the Command window when you made the menu selection. Of
course, you could have bypassed the menu by typing HELP
direcdy into the Command window.
CH. 1
Formats:
CLEAR
CLEAR ALL
CLEAR FIELDS
PI PAD
LLtAK PPTQ
bt1O
s
CLEAR MEMORY
CLEAR MENUS
CLEAR POPUPS
CLEAR PROGRAM
CLEAR PROMPT
CLEAR TYPEAHEAD
CLEAR WINDOWS
CLEAR
The CLEAR command without arguments erases the screen or the current output
4. For now, you just want to use the editor to copy the simplest
form of this command. Move the cursor to the word CLEAR
in the Formats list. Then hold down Shift and press End to
mark the word. Select Copy from the Edit menu to copy the
marked text. Then Press Esc to close the Help window (or
click the close control with the mouse).
GETTING A CQUAINTED WITH FOXPRO 37
QUITTING
To name a field, 46
use up to ten characters, including letters, whole numbers, and
the underscore character. The name must begin with a letter,
and FoxPro does not distinguish between capital and small let¬
ters in held names.
CREA TING A
SAMPLE DATABASE FILE _
The sample database that you will work with in this book is a list of
employees. This database will be a bit like the database file that any
small business might use, but it will be simplified to save you data entry;
for example, it will not include Social Security numbers. The fields that
are in the database will be chosen to illustrate FoxPro’s capabilities,
rather than as an example of an actual business application.
CREATING A DATABASE STRUCTURE 43
1. If necessary, start FoxPro: first make sure you are in the Fox¬
Pro directory (if you are not, enter CD\FOXPRO), then
enter FOXPRO (or FOXPRO-T with Version 1.01) to start
the program.
4. To create your new database file, select New from the File
menu. FoxPro will display a dialog box with radio buttons to
let you choose what type of file to create, as shown in Fig¬
ure 2.1. The dot in the parentheses next to the word Data¬
base shows that it is the default file type.
44 MASTERING FOXPRO
CH. 2
a Discussions of Fox¬
Pro commands
in its upper left corner. Though the Command window is partly cov¬
ered now, you will notice later that the command CREATE Untitled
has been generated.
usually use angle brackets If you were working from the Command window, you could have
to indicate words that must created a new database file simply by entering CREATE plus the
be filled in. CREATE
Kfile name>, for example, name you want the database to have. When you work from the menu
indicates that you would system, however, the file initially has the name Untitled, and you
enter the word CREATE give it an actual name only when you save it. The command
followed by whatever name
you use for the file. Do
CREATE <file name> is used only to create database files. When you
not type the brackets enter a new file name in this manner, the program automatically
themselves. adds the extension .DBF to the name you give the hie.
CREATING A DATABASE STRUCTURE 45
You should also notice that the menu bar has changed. Only the
menu pads for System, File, and Edit are left from the original menu
bar, and a new menu pad for Structure is added to their right.
HO W TO DEFINE THE
STRUCTURE OF A DATABASE
As you can see, the Structure dialog box has columns headed
Name, Type, Width, and Dec (for number of decimal places). To
define the database structure, you simply fill them in for each of the
fields in your database file. The first line describes the first field in
each record, the second line describes the second field, and so on.
Normally, you simply fill out the field definitions in sequence, from
the first in each record to the last, but it is possible to move among the
fields—for instance, to make changes in a definition before saving it. To
do this from the keyboard, use Tab to move one column to the right (or,
if you are in the last column, to the first column of the next line), or
Shift-Tab to move one column to the left. Use the up and down arrow
keys to move up and down the list. Of course, you can also use the
mouse to move the cursor.
46 MASTERING FOXPRO
CH. 2
You can use the Insert text button in the dialog box to insert a new
field or the Delete text button to eliminate a field you already typed.
You can also insert or delete fields via the Structure menu popup. In
fact, if you select the Structure menu pad, you will see that the only
two options on the Structure popup are Insert Field and Delete Field,
as shown in Figure 2.3. (These options offer the hot keys Ctrl-I and
Ctrl-D; for keyboard users, this is faster than using the text buttons.)
You will use the Structure menu popup later in this chapter when
you are modifying the structure of a database.
Figure 2.3: The Structure menu with the Structure dialog box.
Z valid
UP_DOWN valid
When you begin to enter a field name, Character and 10 are auto¬
matically filled in under Type and Width respectively. You can
change the type by using a popup; the width changes automatically
depending on the type you select. The data types and their default
widths are summarized in Table 2.2.
Default
Data Default Decimal Change
Type Width Places Defaults?
Numeric 8 0 yes
Float 8 0 yes
Date 8 n/a no
Logical 1 n/a no
CH. 2
DATA TYPES
The Type column must contain one of FoxPro’s six data types.
The data type you choose determines what you can enter into the
field.
FoxPro uses only 16 • Numeric: may contain numbers and a decimal point, and
significant digits may also begin with a + or - sign. The maximum width of
internally and rounds
numeric data wider than
a numeric field is 20 characters. The decimal point and + or
this. Though these are - sign each take up one place, so you must take them into
more than enough signi¬ account when you define the field width. If you want a field
ficant digits for most
to hold amounts of money less than one thousand dollars, for
business uses, there are
many scientific or statisti¬ example, it must be six places wide: three for the dollar
cal calculations where amounts, one for the decimal point, and two for the cents.
rounding might create
Add an extra place if you want to indicate + or - amounts.
errors. When in doubt
about potential rounding Note that a field that has a decimal point and a leading + or
errors, use the Float type. - sign can hold a maximum of 18 numeric digits (20 maxi¬
mum minus 2).
• Memo: may contain any amount and type of data. The only
limit to the length of a memo field is the amount of disk space
you have. Like a character field, a memo field may include
the null character and binary data; thus advanced users can
use FoxPro memo fields to hold types of data that could never
before be manipulated with database management pro¬
grams, such as scanned images or digitized sound. In ordi¬
nary uses, memo fields act as variable-length character fields,
and they can be manipulated using any of the functions that
are used to manipulate character fields.
For every field you define, there is space taken up on the disk for the
entire width you specify, even if there is little or no data in the field.
Certain fields have unalterable widths: the logical type will always be
one character wide, and the date type will always be eight characters
wide. Memo fields, though they can hold any amount of data, are
automatically defined as ten characters wide. The ten spaces reserved
for it in the database file are just used to point to the location in a sepa¬
rate, variable-length file where the actual data for that field is kept.
When you are entering data, the memo field at first appears to be only
ten spaces long, but if you press Ctrl-PgDn when the cursor is on that
field, you open a special memo window, as illustrated in Figure 2.4, to
allow you to enter any amount of text (or other data); closing the
memo window returns you to ordinary data entry.
50 MASTERING FOXPRO
CH. 2
Because a memo Database files automatically get the extension .DBF (which stands for
field is not kept in
database hie). For example, when you name your sample employee list
the same file as the rest
of the database, there is a
file EMPLIST, it will be stored with the name EMPLIST.DBF. Fox¬
danger of losing your Pro memo files are given the extension .FPT (for FoxPro text). When
memo data when you are you create your EMPLIST database later in this chapter, then, it will
copying a database file—
for example, to transfer it
actually be stored in two files: EMPLIST.FPT as well as
to another computer. You EMPLIST.DBF. In earlier dBASE compatible programs, memo files
must be sure to copy the were given the extension .DBT (which stands for database text). These
memo file as well as the
.DBT files could hold only character data.
database file, and the
easiest way to do this is by Since FoxPro memo files can hold any data type-character or
using the DOS wild-card binary—FoxPro can use databases with these older forms of memo
character. For instance, to
field without any difficulty.
copy a database file named
SAMPLE, use the DOS When you are entering the definition of your sample database file,
command COPY SAM¬ you will see that the cursor does not even move to the Width column
PLE. *, which will copy for date, logical, and memo fields, since their widths are preset and
SAMPLE.DBF and
cannot be changed.
also SAMPLE. FPT or
SAMPLE.DBT. No doubt, you have noticed that an actual piece of data can some¬
times go into several different types of field. For example, numbers
can go into character, numeric, or float fields, and dates can go into
date or character fields. The real difference between field types lies in
CREATING A DATABASE STRUCTURE 51
how the data can be used. You can perform numeric calculations, for
example, only on numeric or float fields—not on numbers that are
stored in character fields. In the earliest versions of dBASE, dates
were stored as characters, and there was no date type. As a result, it
was hard to arrange records in order of date. Now that there is a spe¬
cial date type, though, you can not only sort records in order of date,
you can also perform calculations with dates—to find the number of
days between two dates, for example.
When you are defining the structure of a database, it is best to use
the numeric type only for fields that will actually have calculations
performed on them. Beginners are often tempted to define the zip
code field as numeric just because it has numbers in it. Actually,
though, some zip codes—those from foreign countries—contain let¬
ters as well as numbers, and extended zip codes include a dash after
the first five digits. Neither of these could be entered in a numeric
field. Furthermore, because data in a character field can be sorted
alphabetically and by number, it is possible to sort any zip code in
order when Zip is a character field. There is no advantage, then, to
using a numeric field except for the ability to perform calculations.
CH. 2
may well want to list just the people who live in a certain city or a cer¬
tain state, and you usually want to print mailing labels in order of zip
code; you can do these things if you have a separate field for each.
There are costs to creating fields for which you rarely have data—
fields that, in many records, will be empty. For one thing, it takes
data entry time to skip that field and leave it empty. In addition, a
field takes up space on your disk whether there is any data in it or not.
To save disk space, it is best not to create unnecessary fields and not
to make fields wider than necessary.
Balance the advantages and disadvantages of breaking down your
data. When in doubt, it is generally safest to break the data down
more, rather than less.
• Use the right arrow key to move the cursor. The whole word
will no longer be highlighted; instead, a cursor will appear on
one letter of the word. This allows you to use the ordinary
editing keys to make changes one character at a time.
When you use the first method above to change the data type, all
you have to do is type the first letter of a data type, and FoxPro will
automatically fill in its entire name. If you do not remember all the
data types, you can press the space bar, and a popup will appear to let
you choose among the different FoxPro data types.
The default width will change depending on the data types. If you
choose the numeric or float data type, a default value of zero will
appear for the number of decimal places, but you will be able to edit
it. On the other hand, to accept a default value, just move the cursor
to the next item.
Structure: Untitled
Name Type Width Dec
Field
t F Character 10
<Insert>
<Delete)
« OK »
<Cancel)
Figure 2.5: The default data type and width appear as soon as you start typing.
54 MASTERING FOXPRO
CH. 2
2. You need to change the width from 10 to 15. When you have
finished typing the field name, press Tab twice to move to the
Width column. Press the right arrow key to change from a
highlight to a cursor, which will be on the first digit. Press the
right arrow key again to move to the second digit, press Del
to delete the zero that is there, and type 5 to replace it. The
number will now be 15.
6. Type CITY. Press Tab twice. As the width, type 20. Press
Tab to move to the next line.
8. Type ZIP. Press Tab twice. Type 5 as the width and press
Tab to move to the next line.
B If you have a
mouse, you can use 9. Type DATE_HIRED. The first time through, you should try
it to move to the Type
using the popup to change the data type, to get used to it and
column, use the popup,
and make your selection to give you an idea of another place to find the type names
from it—in the same way listed. Press Tab to move to the Type column, and then press
as you do when you are the space bar to use the Type popup, illustrated in Fig¬
using a menu popup.
ure 2.6. Press the down arrow three times, and then press the
Most people, though,
once they leam the names space bar to select the Date type. Notice that the width auto¬
of the data types, find it matically becomes 8 and the cursor moves to the next line:
easier to use the keyboard
because there is no choice of width for date fields, the cursor
when they are doing this
sort of steady typing. moves down to the next field.
CREATING A DATABASE STRUCTURE 55
Structure: Untitled
Name Type Width Dec
Field
FNAME Character 15
LNAME Character 20 <Insert>
ADDRESS Character 25
APT_NO Character 5 <Delete>
CITY Character 20
STATE Character 2
ZIP 5
DATE HIRED ♦Character 0 « OK »
Numeric
Float <Cancel>
Date
Fields: 8 Logical Available: 3897 OX
Memo d
Picture
a In the Width
column of a
10. Type WAGE. Press Tab to move to the Type column. Type
N for numeric type. (The whole word—NUMERIC—is
numeric field you must
count spaces for the
automatically displayed.) Notice that the default width is 8.
decimal point and deci¬ Since we will assume that everyone’s hourly wage is under
mal places if there are to 100 dollars, we need a width of 5: two for the dollar figures,
be any. Thus, the deci¬
one for the decimal point, and two for the cents. Type 5 and
mal places you count for
the Dec column are not press Tab to move to the Dec column. Type 2 and press Tab
additional to the number to move to the next line.
in the Width column.
11. Type PROBATION. This is a logical held to see whether or
not the employee is on probation. Press Tab to move to the
Type column and type L make it a logical held. Notice that
the width is automatically 1. Because you cannot change the
width of a logical held, the cursor automatically moves to
the next line.
12. Type NOTES. Press Tab to move to the Type column and
type M to choose the Memo type. The width of a memo held
is listed as 10, even when it is holding much more than that,
as you will see. There is no need to change it.
56 MASTERING FOXPRO
CH. 2
13. When you choose the Memo type, the cursor moves to the
next line and the list scrolls up to make room for the descrip¬
tion of another field, but we have all the fields we need for this
sample database. The Structure dialog box should look like
Figure 2.7.
14. Scroll up to the top of the list of fields you entered in order to
see if they are all correct. If you made any typographical
errors, correct them in the same way that you changed the
default values—either by typing the new value when the field
is highlighted, or by pressing the right arrow key and then
editing the existing value.
15. When you have confirmed that the definition is right, select
the default text button, OK, either by clicking it with the
mouse or by pressing Ctrl-Enter.
Structure: Untitled
Name Type Width Dec
Field
X ADDRESS Character 25
X APT NO Character 5 <Insert>
X CITY Character 20
X STATE Character 2 <Delete>
X ZIP Character 5
X DATE HIRED Date 8
X WAGE Numeric 5 2
X PROBATION Logical 1 « OK »
X NOTES Memo 10
<Cancel> d
Figure 2. 7: The structure dialog box with fields filled in. (Not all field names
are visible.)
CREATING A DATABASE STRUCTURE 57
directories, as shown in Figure 2.8. (Of course, your list may look a
bit different from this illustration, depending on what is in your
directory.) The list on the left side of the dialog box lets you navigate
through the DOS directory structure, so you can save your file in any
subdirectory. The place where your cursor is located in this dialog
box is a text box without the box around it, the place for you to type
in the file name. For readers who are not familiar with DOS sub¬
directories, the next section contains a brief discussion of how they
are organized; if you are familiar with DOS subdirectories, skip to
the following section, “How to Save the File.”
►[..] Drive
[TEMPLCOD]
DEMO.DBF
FOXHELP.DBF
FOXUSER.DBF Directory
MONITOR.DBF
M0NIT0R2.DBF
PROINST.DBF «
[ ] All Files
Figure 2.8: The dialog box for naming the new database file.
CH. 2
a To be even more
complete, you can
a parent of the directories below it. The directory at the top is called the
root directory.
The root directory is represented by the backslash \ symbol. Other
include the disk letter
followed by a colon before directories are referred to by listing all the directories above them,
the directory name. For
beginning with the root directory; each of these directories is sepa¬
example, C:\ is the root
directory of the C disk and rated by backslashes. For example, your root directory has a FOX¬
A:\MISC is the MISC PRO directory under it, which has a TEMPLCOD (Template
subdirectory directly under Code) directory under it. The TEMPLCOD directory is referred to
the root directory of the A
disk. If use several disks—
precisely as \FOXPRO\TEMPLCOD. If TEMPLCOD had a
for example, if you have directory under it named MISC, then the full name of that directory
more than one hard disk— would be \FOXPRO\TEMPLCOD\MISC. Figure 2.9 illustrates
it is good to get in the habit
a directory structure with these directories plus a few others.
of including the disk letter
in the directory name, as it By default, DOS commands apply only to the current directory
will let you access the For example, the command
directory you want no
matter what disk you are
DEL FiLE.TXT
in. Here, we assume that
you work in one disk and
do not need to include the would delete the file named FILE.TXT only if it were in the current
disk letter. directory. You can enter the full directory name, though, to use
DEL \FOXPRO\TEMPLCOD\MISC\FILE.TXT
would work no matter what directory you are in when you enter it.
Note that a space must follow any command word, but no spaces
should occur within a file name or path.
A useful shortcut is to use two dots to refer to the parent of the cur¬
rent directory. The two dots (periods) stand for the entire name of the
RD \FOXPRO\TEMPLCOD\MISC
would remove that directory no matter which directory you were cur¬
rently in. If you were already in the \FOXPRO\TEMPLCOD
directory, though, you could remove it by just entering RD MISC.
That is really all you will ever need to know about DOS directories.
You used MD \LEARNFOX earlier in this chapter to create a directory
to use with this book. You can use RD \LEARNFOX to remove that
directory when you are done with this book and have deleted your
practice files. And you should understand the directory structure well
enough that you will have no trouble moving through it.
60 MASTERING FOXPRO
CH. 2
1. The cursor should be at the lower left of the dialog box called
up by selecting OK from the Structure dialog box. Type
EMPLIST as the name of the database.
2. Move to the list of directories. Select the first item in the list,
[..]. You have now moved from the FOXPRO directory up
to the root directory.
3. This list is alphabetical. Select [LEARNFOX] from it, and a
new scrollable list representing the contents of this directory
appears. Of course, there are no files or subdirectories in this
new directory, just [.. ] to let you move up to the parent direc¬
tory, as in Figure 2.10.
4. Now that you have the proper file name (EMPLIST) and
subdirectory (LEARNFOX), just select the default text but¬
ton, Save, to save the new database file.
CREATING A DATABASE STRUCTURE 61
5. FoxPro will save the file and ask if you want to enter records
now, as in Figure 2.11. Select the No text button. (You can
do this simply by pressing the letter N.)
A BIT OF EXPERIMENTING
1. Select Open from the File menu and note that EMPLIST-
.DBF, the file you just created, is dimmed in the scrollable list in
the Open dialog box. Try to select it, and you will see that it
is impossible: the file is already open. Press Esc to close the
dialog box.
2. Enter DISP STRU in the Command window, and FoxPro
will display the structure of the EMPLIST file, as shown in
Figure 2.12—another indication that this is the current file.
CH. 2
Select database:
Drive C
Directory LEARNFOX
« Open »
I
< Cancel Hand
[ ] All Files
CLEAR
DISP STRU
Normally, you would use the menu system to define the structure
of a new database file, but there are cases where it is easier to work
from the command line. For instance, if you are creating a new data¬
base file that is similar to an existing one, you can work from the com¬
mand line to copy the structure of an existing file to a new file. The
FoxPro menu system does not offer an option to enable you to copy a
file structure directly. As you will see in Chapter 5, it is possible to use
the menu system to trick FoxPro into copying the structure, but it is
simpler just to use the command COPY STRUCTURE from the
Command window, as you will do in the following exercise. After
you copy the structure of an existing file to a new file, you will use the
menu system to modify the copy somewhat, a procedure that will
address a common need in practice.
CH. 2
Now that you have copied the structure of an existing database file
to a new one, you will practice modifying it slightly using the Setup
dialog box (shown in Figure 2.17) from the Database menu popup.
This dialog box gives you control over the way in which a database
file is displayed. It is very powerful and versatile. It will be further
Database: TEMP
Structure: <Modlf|> Indexes: Index
System Structure
L
USE C:\LEARNFOX\TEMP.
MP.DBF I
CH. 2
the Delete text button, or select Delete Field from the Structure
menu as you did when you were inserting a field. The PRO¬
BATION field disappears. The Structure dialog box should
now look like Figure 2.19. (Note that the LNAME field in our
screen has scrolled up beyond the top of the list box.)
Structure: C:\LEARNFOX\TEMP.DBF
Name Type Width Dec
Field
FNAME Character 15 >
MI Character 1 <Insert> >
ADDRESS Character 25 >
APT_NO Character 5 <Delete> >
CITY Character 20
STATE Character 2
ZIP Character 5
DATE HIRED Date 8 « OK »
WAGE Numeric 5
NOTES 10 <Cancel>
Li Fields: 11 Length: 117 Available: 3883
jl ==JI PLIST.
ILEARNFOX\T
L
USE C:\LEARNFOX\TEMP.DBF
6. Assuming that those are the changes you want, select the
default text button, OK. FoxPro will ask for confirmation
that you want to make the structure changes permanent:
select Yes. FoxPro will display the Setup window again: a
system message in the upper right says “ Database Structure
Modified. ” Remember that there is no need to remove a sys¬
tem message; unlike an alert, it will just go away. Select OK
to confirm what you have done and to remove the Setup dia¬
log box.
Of course, you can also modify the structure of a file you have been
using—for example, if you have been entering five-digit zip codes
and want to convert to extended zip codes. For now, though, you
should be aware that you can lose data when you modify a files
CREATING A DATABASE STRUCTURE 71
If you ever lose data and want to use the backup hies as your data¬
base, you can do so in several ways. One easy one is by using the
DOS command COPY Kfile name>.BAK Kfile name>.DBF, and
Command
USE C:\LEARNFOX\EMPLIST.
COPY STRU TO \LEARNFOX\T
USE C:\LEARNFOX\TEMP.DBF
RUN DIR \LEARNF0X
CH. 2
To delete a record, 99
select Toggle Delete from the Browse menu, or Delete from the
Record menu, or enter the command DELETE. Any of these
actions just marks the current record for deletion.
CH. 3
Fname NANCY
Lname NIXON
Address 1124 GRANT AVE.
Apt no ▼ Command
USE EMPLIST.DBF
APPEND
CHANGE
The Browse mode is designed to let you look quickly through the
entire database file, rather than looking at one record at a time. It dis¬
plays the database in table form so that each record takes just one line, as
shown in Figure 3.2. In the Browse mode, you can see many records at
a time, but you usually cannot see all the fields of each record.
ADDING, EDITING, AND VIEWING DATA 79
BO
I ▼ Command
USE EMPLIST.DBF
APPEND
CHANGE
APPENDING DATA __
If you try to change or browse a database before any records are in
it—for example, the database from Chapter 2 which only has its
fields defined—the Change/Browse window will simply be blank. It
won’t even display the names of the fields to indicate the structure of
the database. You should append a few sample records first, so that
you have something there to change and browse a bit later.
ADDING, EDITING, AND VIEWING DATA 81
Figure 3,3: If no database is in use, FoxPro asks which database you want.
CH. 3
All these features will be very obvious when you use them in the
following exercises. First you will append some data in the ordinary
way, with the fields one above another, as they are in the Change
mode. Then you will append more data with the fields next to each
other, as they are in the Browse mode. Throughout this book we will
refer to the vertical arrangement of fields as the Change mode or dis¬
play and the horizontal arrangement of fields as the Browse mode or
display, in keeping with the “Browse/Change window” terminol¬
ogy. As you will see later, this window can be split to display informa¬
tion in both modes if you wish.
APPENDING DA TA
WITH THE CHANGE DISPLA Y
In the last chapter, you used the FoxPro dialog boxes to move
among subdirectories. Now that you have become familiar with these
operations, you might as well make your work easier by getting into
the LEARNFOX subdirectory to begin with, which will let you
select the database file with less trouble.
Remember that, if 2. To use your sample database, select Open from the File
you are working
menu and select EMPLIST.DBF from the Open dialog box.
from the Command
window, you do not need
(Notice that the command generated in the Command win¬
to include the .DBF dow is USE EMPLIST.DBF. The full name of the database
extension. You can just file \LEARNFOX\EMPLIST.DBF is not needed, as the file is
enter USE EMPLIST,
in the current directory.)
since the USE command
applies only to database 3. To add data to the file, select Append from the Record menu.
files anyway.
The command APPEND is generated in the Command win¬
dow, a Browse menu pad is added to the menu bar, and the
Browse/Change window appears in the special form that it
has when you are in the Append mode, shown in Figure 3.4.
ADDING, EDITING, AND VIEWING DATA 83
Notice that the name of the database file is at the top of this window
and that the record is arranged in what we are calling the Change dis¬
play, with one field above another. The fields are highlighted in
reverse video, so that you can see the maximum length of each
held—the amount of space you have to fill in. The cursor also
appears in the Fname held; it is the ordinary blinking cursor except
that it is in reverse video.
If you hll the entire length of a held, FoxPro beeps and goes on to
the next held. As you will see, this saves a bit of time when you are
It is common when entering helds of a hxed length, such as date helds. FoxPro will not
using dBASE com¬
patible database fields to
accept invalid data in any held. If you try to enter a letter in the Wage
enter blank records. If held or Date_hired held, for example, it will beep and not accept it.
you create a blank record, One important point to note—and one which is unique to the
in FoxPro, the > > will
Append mode—is that, when you begin, all the helds of the record
disappear and the record
will be saved. The > > have the double right arrowhead > > to their left. This indicates that
sign thus makes it easy there is no data entered in the record: if you close the window at this
for you to tell whether
point, that record will not be saved. On the other hand, as soon as
you truly have a blank
record or simply an you enter any data in the hrst held of the record, the >> will disap¬
unused one. pear from all the helds of the current record, and a new record with
84 MASTERING FOXPRO
CH. 3
> > before each field will be added after the current record, as in Fig¬
ure 3.5. This change indicates that the current record is no longer
empty, and that it will be saved when you close the window. This is a
major difference between selecting Append and selecting Change or
Browse, which only let you add a new record by making an explicit
choice from the Browse menu popup for each record to be added.
USE EMPLIST.DBF
APPEND
Figure 3.5: As soon as you enter data, a new blank record is appended.
1. Type Audrey in the Fname field and press Tab. Notice that,
move to the next field,
but you can actually press as soon as you press Tab, the > > signs to the left of all the
Tab, Enter, or the down fields in this record disappear, because this is no longer a
arrow key. As usual, you blank record. At the same time, a new blank record with
should find the one that is
most comfortable for you.
a > > sign before each field is added after it.
7. Type 11600 in the Zip field. Again, FoxPro beeps and moves
to the next field.
9. You want to enter 8.00 in the Wage field. Press the space
bar, then type 8, and then press Tab to keep the two zeroes
there and move to the next field.
10. Type n for no in the Probation field. The letter n appears for
an instant and is then replaced by an F, as FoxPro translates
yes and no answers into True or False logic statements. Fox¬
Pro then beeps to tell you the field is full, and the cursor
moves to the next field. (If you enter anything besides a capi¬
tal or small T, F, Y, or N in a logical field, FoxPro beeps to
show that you have made an invalid entry, and the cursor
stays in the field.)
86 MASTERING FOXPRO
CH. 3
12. Try zooming the window, to get a better feel for word wrap.
Click the zoom control, or select Zoom from the Window
menu. The memo window now takes up the entire screen,
and the text is automatically rewrapped to fit into the new
size of the window, as shown in Figure 3.7. Zoom the win¬
dow again to return it to its original size.
ADDING, EDITING, AND VIEWING DATA 87
13. When you have finished typing, press Ctri-W or click the
close box to close the memo window and return to
the Browse/Change window. Then press Tab to move to the
next field, the Fname field of the second record.
Try entering the following additional names to get used to the way
the Append mode works and to give yourself some sample data to
work with in the rest of the book. Be sure to press the Caps Lock key
first so that you enter the following records as they are written, in all
capital letters (except for the memo fields, some of which are entered
with ordinary capitalization). Where the field indicates “(none),”
leave that field blank.
CH. 3
APPENDING DA TA
WITH THE BROWSE DISPLA Y
You will continue creating your sample database by appending
another record with the Browse display. In this exercise, you will use
the menu system to toggle the screen to this display, and then you will
go on adding records in much the same way you did before.
1. If it isn’t already there, move the cursor to the first field of the
blank record. Then select the Browse menu pad. Since
the Browse/Change window is now arranged in the Change
display mode, the first option on the menu popup is Browse.
Select that option to toggle the window to the Browse display.
c Command
5. Type 1124 GRANT AVE in the Address Field and press Tab.
Then press Tab again to skip the Apt_no field.
12. There is no entry in the Notes field. Leave the cursor in that
field.
90 MASTERING FOXPRO
CH. 3
As you can see, it is equally easy to append records with either the
Browse or the Change display. Now, in order to leave the file in
the way you will next use it, you will toggle back to the Change dis¬
play and then end your data-entry session.
1. Select the Browse menu pad. Notice that the first option on
the menu popup now is Append, which toggles the screen
back to the Change display that is standard in Append mode.
Select the Append option.
2. Close the window to save your changes: press Ctrl-End, click
the close box, or—if you insist on doing things the hard
way—select Close from the File menu.
on last is still the current record—the record with the cursor in it, dis¬
played in the Browse/Change window as shown in Figure 3.9. Fox¬
Pro thus kept track of where the cursor was even after the window
was closed. FoxPro has what is called a pointer, which remains on the
current record until you either move it or close the database. The
idea of the pointer is important, and you will look at it more thor¬
oughly later in this chapter.
The command
CHANGE is exactly
equivalent to the com¬
mand EDIT.
Figure 3.9: The Change window, with the last record you entered still current.
1. Select Change from the Record menu. This will display the
Browse/Change window with the last record that you
entered. Notice that the command CHANGE is generated in
the Command window.
2. Try moving up and down through the file. After moving up,
use the scroll bar or press PgDn repeatedly to try to move
beyond the last record: you will see that you cannot. Try
again, by using the down arrow key to move to the final field
of the last record. When you try to go further, you will see
that you cannot go beyond the last record and add a new
record, as you could when you were in Append mode.
92 MASTERING FOXPRO
CH. 3
If you delete the That’s all there is to editing the content of fields; you can close the
entire contents of a window and save the changes by pressing Ctrl-End or discard them
memo field, the word
memo in the database will
by pressing Ctrl-Q. To edit a memo field, just move the cursor to the
begin with a small m field, press Ctrl-PgDn to access the memo window, and edit the field
again, to show that the just as you did when you were first entering it, using the conventional
field is empty.
editing keys. Save the changes you made by closing the memo win¬
dow, or discard the changes you made by pressing Esc.
A Browse menu pad was added to the menu bar when you selected
Change, just as it was when you selected Append. Most of the
options on this menu popup (shown in Figure 3.10) are far more use¬
ful when you are in Browse mode, and you will look at this popup in
detail in the next section.
System f i lo Edit
Dat..abase Record F’rogram Window Browse
1 E1V1PL 1ST
1 Fname ■CHARLOTTE DDMMHHBHf Browse
I Lname ■sAGORIN grid Off
1 Address ■J20i SHADY LANE Unlink Partitions
Apt_no Change Partition ~H
City
State Size Field
Zip Eove Field
Date_hired Sesize Partitions
Wage
Probation G0to...
Notes Seek . . .
Fname
Lname
WILLIAM
JOHNSON
J|oggle Delete
Append Record |
Address 523 EAST 21 ST.
Apt no F-23 ▼ Command
Figure 3.10: The Browse menu popup when you are in Change mode.
ADDING, EDITING, AND VIEWING DATA 93
You will find that, in general, the only time you will want to use
the menu when you are in Change mode is when you want to add a
single extra record. Try it now:
▼ Command
USE EMPLIST.DBF
APPEND
CHANGE
CH. 3
options for altering the display of the window that are on the Browse
menu popup are also available when you select Change, but they
obviously are more useful when you are browsing through a file and
cannot see the entire record. You should experiment with these
options as you read their descriptions below. Experiment also to see
how they work when you toggle back and forth between Change and
Browse.
When you experiment, the first thing you should notice is that
whenever you select Browse (from the Database menu), the com¬
mand generated in the Command window is BROWSE LAST. This
command can be used to open the Browse window as it was when
you last used it. This command is very useful in practice. For
example, if you often telephone people, and you change the order of
fields in the Browse window so that the telephone number is next to
the name, FoxPro will save the setting even after you turn off your
computer, and will display the fields in that order whenever you
browse that file using BROWSE LAST.
RESIZING AND
CHANGING THE ORDER OF FIELDS
The most common alteration you will want to make in the Browse
window is to change the order and the size of the fields, so you can see
the data you want. If you move the fields that you need to the left,
and you make some of the fields smaller, you can generally see all of
the data that you need within the Browse window. (Sometimes,
of course, you will want to Zoom the window also).
Changing the size or order of fields in this way only affects how
they are displayed in the Browse window, and does not affect the way
that they are actually stored in the database, so there is no danger of
loss of data.
USING A MOUSE
It is extremely easy to change field size or order using a mouse.
You simply use the mouse to manipulate the list of field names above
the records. First, though, check to see if you can see the grid lines
96 MASTERING FOXPRO
CH. 3
to the right of each field name. If you cannot, select the Grid On
option from the Browse menu.
• size: To change the size of a field, move the pointer to the grid
line to the right of the field’s name. Drag left or right to make
the field smaller or larger.
• size: Select Size Field, then select the field whose size will be
changed. The name of the current field is highlighted in
reverse video. If it is not the field you want, use Tab or Shift-
Tab to move to the field you want. Then press the left arrow
key to shorten the field or the right arrow key to lengthen the
field. When it is the size you want, press Enter.
Link; after you have unlinked partitions, you would choose Link
to tie them together again. Figure 3.12 shows the difference between
linked and unlinked partitions.
After you have partitioned the window, only one partition is active
and available for editing. You can move around a partition in the same
way that you move around any Browse/Change window, by using the
scroll bar or by using the Tab, arrow, PgUp, and PgDn keys.
As you can see from the illustrations, the partitioned window is very
versatile. Experiment with it when you read the following sections. The
first section is for mouse users, the second is for keyboard users, and the
third describes menu selections that are the same for both.
USING A MOUSE
Again, it is very simple to work with partitions using the mouse.
CH. 3
Figure 3.12: The Browse/Change window with linked partitions (top) and
unlinked partitions (bottom).
begins to blink, indicating that you can move the partition.
Press the right arrow key, and the window splitter will move
right, dividing the window into two partitions. As you press
the right arrow key, the partition on the left becomes larger
and the one on the right becomes smaller. Keep pressing the
right and left arrow keys until the partitions are the size you
want. Resize existing partitions in the same way. To
Remove the partitions, press the arrow keys until one is
closed.
ADDING, EDITING, AND VIEWING DATA 99
DELETING A RECORD _
There are a few additional features of the Browse menu popup.
Selecting Grid Off removes the vertical lines separating fields in
the Browse window. If you select it while in the Change display, the
lines will be removed when you toggle to the Browse display. After
the lines are removed, this option changes to Grid On, which lets you
replace the lines.
Goto and Seek from the Browse menu popup let you move
through the database file by specifying the records you want and by
using indexes. These options are identical to options available on the
Record menu popup. Goto will be discussed later in this chapter;
Seek will be discussed in Chapter 5.
The most important remaining option on the Browse menu is
Toggle Delete, which lets you delete a record. To be more precise,
selecting this option lets you mark a record for deletion—it does not
actually remove the record from the database file. When a record is
marked for deletion, a bullet appears to its left, as shown in Fig¬
ure 3.13. The menu option is equivalent to the command DELETE.
If a record is already marked for deletion, selecting the same
option will unmark it; that is why it is called Toggle Delete. In this sit¬
uation, it is equivalent to the command RECALL.
100 MASTERING FOXPRO
CH. 3
D▼ Command
Figure 3.13: Bullets show that the first and third records are marked for
deletion.
Using this option from the Browse menu popup is very handy
when you are editing or browsing a file, to delete or recall the record
you are currently working on. In other situations, you may want the
extra power that you get by selecting Delete from the Record menu
and using the Delete dialog box, shown in Figure 3.14.
I The For and While
Selecting the default text button Delete from this dialog box simply
■■I check boxes are the
most useful, as they let you
marks the current record for deletion, just as selecting Toggle Delete
delete or undelete records from the Browse popup does. As you can see, though, this dialog also
that meet certain criteria. includes Scope, For, and While check boxes, which let you mark
For example, you can
more than one record at a time. These three check boxes are found in
delete all the records with
less than a certain wage or many different dialog boxes, and you will learn how to use them
recall the records that are in Chapter 5. To give one example now, though, to give you an idea
not from California. This
of what they can do, select Scope and then choose All from the Scope
is essentially a matter of
building a query into the dialog box to mark all the records for deletion (or just enter the com¬
DELETE command, and mand DELETE ALL in the Command window).
you should bear it in mind
Remember that these records are simply marked for deletion: you
when you read the discus¬
sion of FOR and WHILE
can select Recall from the Record menu to unmark them. The Recall
clauses in Chapter 5. dialog box, shown in Figure 3.15, has the same check boxes as the
Delete dialog box. Selecting its default Recall text button will
ADDING, EDITING, AND VIEWING DATA 101
Audrey -
Lname Address
318 B. 31 St.
1
JACK LOVE 3642 TANACH WAY
EDNA CHANG 2701 ADDISON WAY
CHARLOTTE SAGORIN 2203 SHADY LANE
WILLIAM JO
WILLIAM B. JO
NANCY NI [ J Scope...
JAMES SK « Recall »
[ ] |or...
< Cancel >
[ ] fflhile.
Command
USE EMPLIST.DBF
APPEND
CHANGE
CH. 3
unmark only the current record, however; for this example it is best
to use the check boxes, which let you work with groups of records.
Once again, use a scope of All to unmark all the records that you pre¬
viously marked for deletion.
When you experiment with these features, you will see that Toggle
Delete does not generate a command in the Command window; it
resides entirely in the Browse window. On the other hand, Delete,
from the Record menu, generates the command DELETE NEXT 1
as well as FoxPro “talk” that says “1 records deleted.” Similarly,
Recall, from the Record menu, generates RECALL NEXT 1 as well
as talk that says “1 records recalled.” The NEXT 1 at the end of
each of these commands is not necessary: it specifies the scope of the
commands (discussed at length in Chapter 5) to be 1, which means
that they apply only to the current record. As it often does, FoxPro
generates commands with more detail than is actually needed: this is
the default scope for these commands, so you do not need to specify it
if you are working from the Command window. Thus, to mark or
unmark the current record from the Command window, simply
enter the command DELETE or RECALL.
Data can be lost if Records that are marked for deletion are not actually removed from
packing is inter¬
rupted. Because of this,
the file until you select Pack from the Database menu or enter the com¬
the Esc key is disabled mand PACK in the Command window. When you “pack’ ’ the file, the
during packing: pressing program finalizes the deletion by copying all of the records that are not
Esc will not interrupt the
marked for deletion. These are copied to a new file, which replaces the
PACK command as it
does other commands. old file. The process is called packing because it compresses the file into a
Do not turn off the com¬ smaller amount of space by removing the deleted records. Because it
puter while packing is in
takes time to copy the records to a new file, it is done only when you
progress—no matter how
long it takes. If you think select Pack; if you were working with a long file, there would be an
there is danger of a power annoying delay if the file were packed every time you deleted a record.
failure, back up your
When you pack a database, ‘ ‘talk’ ’ will appear on the screen behind the
database file before
packing.
windows to tell you how many records were copied into the new version
of the database file.
Most FoxPro commands that use records will use them regardless
of whether they are marked for deletion, and this can sometimes
cause problems. For example, if you search for records from the state
of California, FoxPro will find those that are marked for deletion as
well as those that belong in the file. The simplest way of dealing with
this problem is to pack the database before using any command that
t
ADDING, EDITING, AND VIEWING DATA 103
you do not want deleted records to get in the way of. At the end of
Chapter 5, after you have learned about logical expressions, you will
be able to learn other methods of keeping records that are marked for
deletion out of your way.
Finally, there is one very dangerous command that you should
know about: ZAP, which eliminates all records from a file. It is
equivalent to entering DELETE ALL and then PACK, except that it
works much more quickly. After you enter ZAP, your records are
gone forever: they cannot be recalled. This is such a dangerous com¬
mand that it should probably not have been included in the dBASE
standard: since it is used in dBASE compatible programs, though,
you should be forewarned.
ZAP is most dangerous in combination with the environment
command SET SAFETY OFF. Normally, FoxPro will ask you if you
want to ZAP all your records before it executes this command. How¬
ever, if you have entered the command SET SAFETY OFF (or turned
Safety off using the View window) earlier in the session, ZAP will
eliminate all your records without giving you any warning.
There are times when you should know where the pointer is even if
you can’t see it. Furthermore, there are times when you want to
move the pointer.
You have already seen that a pointer keeps track of the current
record when you are changing or browsing a file. After you close the
Browse window, the record that had the cursor on it last remains
the current record as long as the file is still open; thus the cursor will
still be on that record when you start to edit the file again. Likewise,
you have seen that when you enter DELETE in the Command win¬
dow, the record that the pointer is on will be marked for deletion.
This occurs even if the Browse window is closed.
When you are working with the pointer, it is useful to remember
that every record in your database file has a record number. Records are
numbered sequentially as they are entered: the first record you
entered in the database is record number 1, and so on.
It is possible to move the pointer even when the Browse window is
closed and you cannot see the pointer. You do this by selecting Goto
104 MASTERING FOXPRO
CH. 3
from either the Record or the Browse menu popups. Either of these
will display the Goto dialog box, illustrated in Figure 3.16.
As you can see, this dialog box gives you four choices of where to
move the pointer:
Audrey
Lname Address
318 B. 31 St.
I
JACK LOVE 3642 TANACH WAY
EDNA CHANG 2701 ADDISON WAY
CHARLOTTE
WILLIAM
WILLIAM B. ( •) Top
NANCY
JAMES ( ) [|ottom « Goto »
( ) Ikip
USE EMPLIST.DBF
APPEND
CHANGE
Since the pointer is a very important concept, use this dialog box a
bit to get a feel for it. Open the Browse window before moving the
pointer, so you can see where it goes.
2. Select Goto from the Record menu and select one of the radio
buttons of the Goto dialog box. Remember you must select
the default text button, Goto, to execute the command. Do
this several times to get a feel for moving the pointer.
Notice that the commands that are generated as you make selections
from this dialog box are almost identical to the selections you make.
GOTO commands have two forms: as a typing shortcut, you can
simply enter the command GO, though GOTO is also valid.
CH. 3
• SKIP < number > moves the pointer the indicated number of
records from the current record. The number can be positive
or negative.
You will see in the next section that there is an easy way of seeing the
contents of the target record when you are working from the Com¬
mand window, without opening the Browse window.
SHORTCUTS USING
THE COMMAND WINDOW _
There are two commands for viewing the file that are very useful
when you are working in the Command window or programming
and that have no equivalent in the menu system.
would show you only those three fields of all the records in the data¬
base. Notice that the field names must be separated by commas. This
form of the command lets you choose few enough fields that you can
fit them into the width of one screen.
You will see in Chapter 5 that many commands can be used with
this sort of field list. In some cases the word FIELDS must also be
ADDING, EDITING, AND VIEWING DATA 107
added before the list of fields; to avoid having to learn which com¬
mands require it, it is best to include it whenever it is relevant. Thus,
it is easiest to use the command
here, and this is the form these sorts of commands will take through¬
command. Once you get the DISPLAY command right, with the
fields that you actually want, you can move the pointer to a different
record by moving the cursor to the appropriate commands in the
Command window and then reusing the DISPLAY command.
The limitation of the LIST command is that most database hies are
too long to fit on a single screen, and the records in the database will
D To clean up your
printout while also
scroll by on the screen too quickly for you to read them if you use
LIST. It can be genuinely useful, however, if you add TO PRINT at
the very end of the command, which will send the listing to the
making a more useful
record of the listing, you
printer as well as to the screen. This is usually the easiest way of get¬
can use LIST TO FILE ting a quick-and-dirty report on the data in your hie.
Kfile name > instead of LIST normally displays the record number of each record, but you
LIST TO PRINT. This
can make the printed report look better by displaying the helds with¬
version of the command
will create the same out the record number. Do this by adding OFF after the held list and
listing in a plain DOS before the words TO PRINT when entering the LIST command. For
text file (also called an
example, if you have a database of names, addresses, and telephone
ASCII file). The advan¬
tage to this is that you can
numbers, and you want to give someone a printed list of just the
edit this file with any names and phone numbers, the absolutely easiest way to do it is by
word processor that reads entering
plain text files. The word
processor will automati¬
cally handle the page
LIST FIELDS FNAME, LNAME, PHONE OFF TO PRINT
breaks, and if you change
the column headings a bit (assuming, of course, that these are the names of the helds). This will
and add a header or give you a printed list of all the names and phone numbers in the hie,
footer for each page,
you’ll have a fairly
in three columns, with the name of the held at the top of each
respectable looking column. Note that long lists will print continuously, without allowing
report. for page breaks.
108 MASTERING FOXPRO
CH. 3
2. Enter
1. Enter
2. Try editing one of the fields and you will see that is it impos¬
sible. FoxPro just beeps and does not change the data. This is
because you included NOEDIT in your command.
leyy [Audrey
LOVE JACK 16.20
CHANG EDNA 9.75
SAGORIN CHARLOTTE 22.75
JOHNSON WILLIAM 6.25
JOHNSON WILLIAM B. 19.70
NIXON NANCY 18.25
SKINNER JAMES 8.20
k Command
Figure 3.18: The Browse window if you use BROWSE with a field list.
110 MASTERING FOXPRO
CH. 3
There are many other options of this sort that you can use from the
command line. If you are interested in them, see BROWSE, EDIT
(or CHANGE), and APPEND in Appendix C. Field lists can be used
with many other commands besides these, and they will be covered
in more detail in Chapter 5.
t
U nderstanding
Indexes and Expressions
*
M
CH. 4
Some indexes are more complex than others. For example, if you
want to use names in alphabetical order, you would not only index on
the last name: in order to make sure that Aaron Smith comes before
Xavier Smith, you need to use the first name as a “tie-breaker” to
determine the order of records whose last names are the same. Fur¬
thermore, as you will see, a name entered using lowercase letters
UNDERSTANDING INDEXES AND EXPRESSIONS 117
would come after a name that is entered in all capital letters. In the
next section, you will learn to use expressions, which let you deal with
this sort of problem.
To begin with, though, you can create a couple of simple indexes,
each of which is based on a single field. Let’s say that you need to use
the records in zip code order when you produce your mailing labels,
and that you also need to produce a special report that uses the
records in order of the date the employee was hired. Try creating
these indexes:
CH. 4
INDEX ON:
LNAME c
ADDRESS c
APT NO c « OK »
CITY c
STATE c < Cancel >
1 ZIP C
l
<@xpr. . . > ZIP
[ 3 Enique
<flor... > ommand
ST.DBF
M
DBF
1
Figure 4.2: Naming the index file.
UNDERSTANDING INDEXES AND EXPRESSIONS 119
CH. 4
* Command
_jN ZIP TO C:\LEARN
BROWSE LAST
INDEX ON DATE_HIRED TO C
BROWSE LAST
Perhaps you were curious about why the Index On dialog box that
lets you name the index includes a scrollable list of the names of exist¬
ing indexes. You can choose one of these names if you want to over¬
write an existing index, replacing it with an index of the same name
based on the expression you have created—as you will do later in this
chapter, when you index by name in two different ways.
There are two other features of this dialog box that you do not need
to worry about for now. The For text button lets you index only
records that meet certain logical criteria; this is essentially a matter of
building a query into an index, which will be covered in Chapter 5.
The Unique check box excludes records with duplicate values in the
field that you are indexing on; thus, only the first record that FoxPro
finds with a given value in that field is indexed. This is an advanced
UNDERSTANDING INDEXES AND EXPRESSIONS 121
UNDERSTANDING EXPRESSIONS _
Though simple indexes are useful for many purposes, there are
times when they are not adequate—times when you want to index on
an expression rather than just on a field. As you have seen, you can¬
not simply index on the Lname field to put the records in alphabetical
order, since you also have to use the Fname field as a tie breaker.
In addition, you must make the index put capital and small letters
in proper alphabetical order, since, by default, FoxPro indexes
in ASCII order. You will be better at using FoxPro if you take a
moment to understand what this means. ASCII stands for American
Standard Code for Information Interchange. Just as Morse code rep¬
resents each letter with a series of dots and dashes, ASCII represents
each character with a number. The lowest numbers represent what
are called control characters, such as carriage return. The first of the
122 MASTERING FOXPRO
CH. 4
• field names
• memory variables
• constants (or literals)
• functions
• operators
Field names, of course, are simply the names that you gave the fields
of your database, such as FNAME and LNAME. As you will see,
the names of all the fields in the database you are working with can be
9 FoxPro automati¬
cally creates certain
selected from a scrollable list in the expression builder dialog box.
Memory variables are used in more advanced expressions, and are
CH. 4
When you are working with constants, you have to remember that
an entire expression must be of a single data type. Sometimes you
must convert literals or fields from the date or number type to the
character type in order to make them compatible with the rest of
the expression. This is where functions come in handy.
r
I
IN
tL
ABS()
ring Logical Date
ACOS()
ASC( )
ASIN()
F AT( , ) Database: Variables:
ATC(,. )
► FN ATCLINE(,) EMPLIST ►_ALIGNMENT C
LN ATLINE(. ) BOX L
AD ATAN() -INDENT N
AP ATN2(, ) < Verify > _LMARGIN N
Cl BAR( ) PADVANCE C
ST CEILING() « OK » “PAGENO N
ZI C0L() J>BPAGE N
DA COS( ) < Cancel > PCOLNO N
DIFFERENCE(.)
DISKSPACE()
ERROR()
-▼-
"text"
p +
Math gical Date
ft
r INDEX ON: <expr" ALIASt)
ALLTRIM()
CHR( )
CHRTRAN(, )
CURDIR()
□
Field Names: DBF( ) Variables:
FIELD()
►FNAME c Pj FILTER() ►—ALIGNMENT C
LNAME c n FGETS(,) -BOX L
ADDRESS C 1 FKLABEL( ) -INDENT N
APT NO c I FREAD(, ) -LMARGIN N
CITY c 1 FULLPATH(, ) -PADVANCE C
STATE c 1 GETENV( ) -PAGENO N
ZIP c 1 GETFILE(, ) _PBPAGE N
DATE HIRED D | LEFT(, ) PCOLNO N
LOWER()
LTRIM()
MESSAGE( )
-▼-
Figure 4.6: The Math, String, and Date popups in the expression builder
dialog box.
FUNCTIONS
S A function does not
actually transform or
A function returns a value. Usually this means that a function
works on a piece of data in some way and that the ‘Value” it returns
permanently change the
is the data in a new form. For example, the index you create at the
data it is working on. It
merely lets the expression end of this chapter will use the function UPPER() to convert lower¬
use it in this new form. case characters to uppercase. You will use this function in the form
UPPER(LNAME) to return the data in the Lname field with all the
System File Edit Expression
Figure 4.6: The Math, String, and Date popups in the expression builder
dialog box. (continued)
THIS IS A TEST
12/12/90
CH. 4
THIS IS A TEST
12/12/90
william
523 East 21 St.
The next group of functions are useful for trimming blanks from
character data. This is often necessary, because when you tell it to
print the held Lname, for example, FoxPro not only prints the char¬
acters that are in the held, it also adds enough blanks at the end to hll
the entire width of the held. These are called trailing blanks. Relat-
edly, if you convert a numeric held to the character type, FoxPro
often adds blanks to the left of the number to pad it out. These are
called leading blanks. Although there are times when blanks
are indispensable (as you will see when you create your next index),
there are also times when you want to get rid of them.
If you want, for example, to produce mailing labels or reports without
unnecessary blank spaces in them, you would use these functions:
The next group of functions is useful for converting data from one
data type to another, which is necessary when you are creating an
expression that combines data that is originally of two different types:
CH. 4
THIS IS A TEST
12/12/90
william
523 East 21 St.
THIS IS A TEST
THIS IS A TEST
You will be trying out a few of these functions in the next section
when you use operators to create more complex expressions. For
now, you should try the STR() and VALQ functions, which are quite
commonly used.
Next are a few functions that you will want to use on occasion to
manipulate dates.
CH. 4
8 records indexed
8 records indexed
THIS IS A TEST
12/12/90
william
523 East 21 St.
THIS IS A TEST
THIS IS A TEST
6.25
6
6.25
10.00
You have already tried DATE(). Take a minute now to try out a
couple of other date functions:
Finally, two other functions that you might find instructive, even if
they are not necessary, are ASCQ, which returns die ASCII number of
any character, and the opposite function CHR(), which returns the
UNDERSTANDING INDEXES AND EXPRESSIONS 133
THIS IS A TEST
12/12/90
william
523 East 21 St.
THIS IS A TEST
THIS IS A TEST
6.25
6
6.25
10.00
Wednesday
April
CH. 4
get rid of these leading blanks. The double parentheses at the end
might seem a bit confusing at first, but if a complex expression con¬
fuses you, remember that it is evaluated from the inside out. First
look at the innermost function, STR(WAGE,5,2) in this case. Once
you understand that this is a number converted into string form, it is
easy to see what LTRIM0 is doing to it.
OPERATORS
The word “operators” sounds very technical and forbidding, but
even if you have never used a computer before, you are already
familiar with some operators, such as + and -, which are used to
THIS IS A TEST
12/12/90
william
523 East 21 St.
THIS IS A TEST
THIS IS A TEST
6.25
6
6.25
10.00
Command
Wednesday
April
6.25
6.25
Wednesday
+ addition
- subtraction
* multiplication
/ division
~ or exponentiation (raising to a power)
* *
2x3 + 4
136 MASTERING FOXPRO
CH. 4
If you’re familiar with the math, you know not to multiply 2 times x
first and then cube the result. Without any thought, you would cube
the value of x first, then multiply the result by 2, and then add 4. This
is the same order of precedence as in FoxPro: exponentiation, then
multiplication or division, then addition or subtraction.
In general, though, it is good to use parentheses to indicate precedence
even if the operations would occur in that order anyway, simply
to make the expression easier to read. For example, (2*WAGE) +4
gives the same result as 2*WAGE +4, but it is easier to understand
immediately when you read it. Likewise, because spaces are op¬
tional before and after operators, you should use whatever spacing
you need to make the expression easy to read.
Using the arithmetic operators with ? acts as a simple calculator, as
shown in Figure 4.13:
THIS IS A TEST
12/12/90
william
523 East 21 St.
THIS IS A TEST
THIS IS A TEST
6.25
6
6.25
10.00
Wednesday
April
6.25
6.25
Wednesday
16
0.33
String operators are used to concatenate strings, that is, to put two
strings together as one.
FNAME - LNAME
is the same as
TRIM(FNAME) + TRIM(LNAME)
138 MASTERING FOXPRO
CH. 4
william
523 East 21 St.
THIS IS A TEST
THIS IS A TEST
6.25
6.25
10.00
Wednesday
April
6.25
6.25
Wednesday
16
0.33
12/19/90
since these fields only have trailing blanks to trim. When you actually
work with FoxPro, you will find this shortcut very convenient. In this
book, though, we will generally use the + operator to concatenate
strings and will use functions to trim unnecessary blanks, in order to
get you accustomed to the trimming functions and to give you more
insight into what is happening when you concatenate strings.
Note that the string operators must be fiddled with a bit to print a
full name, since a simple - concatenation would not leave a space
between the strings. To print a name, you have to include a blank
space as a constant. For example,
2. Enter
3. Enter
THIS IS A TEST
THIS IS A TEST
6.25
6
6.25
10.00
Wednesday
April
6.25
6.25
Wednesday
Command
16 - {05/06/90
0.33
Oporator/oporand typo misma t.ch.
31 " + DATE( )
12/19/90 ■ ■ r
CH. 4
4. Enter
takes up more than one ? "The hourly wage of" + TRIM(FNAME) + " " +
line on a printed page, TRIM(LNAME) + " is " + LTRIM(STR(WAGE,5,2))
you should of course type
it as a single command The function TRIM() has eliminated the unnecessary
without hitting Enter blanks, but notice that you had to add a literal blank between
until you reach the end of
FNAME and LNAME so it did not come out
the whole thing. As long
as it is less than 255 WILLIAM JOHNSON
characters long, it will all
fit in the Command Likewise, do not forget to include the spaces after of and
window; you just have to before and after is.
scroll to see the entire
command. 7. Edit the command once more to get the capitalization right
and to add a dollar sign and a period at the end: Enter
? "The hourly wage of" + PROPER(TRIM(FNAME) + " "
+ TRIM(LNAME)) + " is $" + LTRIM(STR(WAGE5,2)) +
✓/ //
6.25
10.00
Command
? "The hourly wage of + FNAME + LNAME + " is " + WAGE
? "The hourly wage of + FNAME + LNAME + " is " + STR(WAGE)
? "The hourly wage of + TRIM(FNAME) + " " + TRIM(LNAME) + " is ' LTRIM(STR
? "The hourly wage of + PROPER(TRIM(FNAME) + " " + TRIM(LNAME)) ’ is $" +
16
0.33
31
12/19/90
Today is 12/12/90
ALPHABETIZING BYNAME
As you have seen, to put your records in alphabetical order, you
need to index by last name using the first name as a ‘ die-breaker’ ’
when last names are the same. The way to do this is to index on the
expression LNAME + FNAME.
FoxPro alphabetizes by comparing the ASCII numbers of charac¬
ters in a word. The ASCII number for the blank character comes
before any of the characters that represent letters, and this fact is vital
142 MASTERING FOXPRO
CH. 4
S You could
also index on
or the - operator when you are indexing alphabetically by name.
In ASCII order, small letters all come after capital letters. To make
the expression
sure that your list is alphabetized in dictionary order, rather than
UPPER(LNAME) ASCII order, you should use the function UPPER() to capitalize the
+ UPPER(FNAME), letters of the expression that you are indexing on. In the next
which is identical to
example, you will start off by indexing on LNAME + FNAME , to
UPPER(LNAME
+ FNAME). see what ASCII order looks like, then you will index on the expres¬
sion UPPER(LNAME + FNAME), to get proper dictionary order.
Though these are simple expressions, you will create them the long
way in order to get experience with the expression builder dialog box,
illustrated in Figure 4.17. As you have seen, the expression builder
includes four popup controls across the top, which let you access the
1
I Math String Logical Date
►FNAME C EMPLIST
LNAME C
ADDRESS C
APT_NO C < Verify >
CITY C
STATE C « OK »
ZIP C
DATE HIRED D < Cancel >
CH. 4
7. Since this is the expression you want to index on, select the
default OK text button. The expression builder dialog box
disappears, and the expression that you generated is filled in
to the right of the Expr text button of the Index On dialog
box. (Remember that you could have just typed the expres¬
sion in here, rather than using the expression builder.)
9. The Index File Name dialog box appears. You do not need to
change the drive or directory: just type NAMES as the name
of the new index. Then select OK. The command
10. To check the effect of the index, select Browse from the Data¬
base menu. Notice that all the names are now in alphabetical
order except Audrey Levy’s. JACK LOVE comes before
Audrey Levy, as shown in Figure 4.18, because capital LO
comes before Le in ASCII order. Close the Browse window.
L Select Open from the File menu, then the popup control
(which now says Database), and then Index. (Notice, inci¬
dentally, the text button New: you can also create new
indexes with this dialog box, as you will in the next step.)
UNDERSTANDING INDEXES AND EXPRESSIONS 145
▼ Command
hourly wage of "
CLEAR
INDEX ON emplist->lname
BROWSE LAST
3. Select the String popup control. Scroll down and select the
UPPER() function from the popup. Notice that die cursor is
now in the UPPER() function’s parentheses in the expres¬
sion box.
CH. 4
Open:
[••] Drive
DATES.IDX
NAMES.IDX
•ZIPS. IDX
Directory LEARNFOX
« Open »
list->lname
1
BROWSE LAST
5. Press the left arrow key once to move the cursor back one
space into the parentheses. Select the String popup control
and select + from the popup. The + goes into the parenthe¬
ses, and the cursor moves out of the parentheses again.
6. Press the left arrow once again to move the cursor back into
the parentheses. Select FNAME from the scrollable list of
fields to complete the expression you want. Select Verify to
make sure it is right.
dimming by typing its name in the text box, FoxPro will dis¬
play an alert and refuse to overwrite an index that is already
open.)
Select Browse from the Database menu and you will see that
the records are now in proper alphabetical order, not ASCII
order. Audrey Levy is now before JACK LOVE, as in Fig¬
ure 4.21. Close the Browse window.
Going through the steps of recreating the index was a useful lesson
in using the expression builder, but it also shows that it is sometimes
easier to use the Command window. You could have created the new
index by closing the first index, pressing the up arrow key to move
the cursor to the command
Drive c I
L DATES.IDX
C:\LEARNFOX\NAMES.IDX already ( ■x i s ts ,
overwrite it? • c ■' '■ ' ¥ s
NAMES.IDX
list->lname
L
SET INDEX TO ZIPS.IDX
CH. 4
EDNA
Lname
ICHANG
Address
T Command
■■■CDlast
SET INDEX TO ZIPS.IDX
INDEX ON UPPER(emplist->
BROWSE LAST
1. As you did earlier, create the index by selecting New from the
File menu then the Index radio button, and the OK text but¬
ton. From the Index On dialog box, select the Expr text
button to call up the expression builder.
2. Simply type 100 in the text box. Then use the Math popup
control and select - . Then use the scrollable list of field
names and select WAGE. The expression should now read
100 -- emplist - >wage. (Of course, you could have just
typed in 100 - WAGE at the Expr text button.)
3. Since this is the expression you want to index on, select OK.
From the Index On dialog box, select OK to create this
index. In the Index File Name dialog box type WAGES as the
name of the new index. Then select OK.
CH. 4
▼ Command
UPPER(emplist->
BROWSE LAST
INDEX ON 100 - emplist->
BROWSE LAST
If you wanted to, you could do the same thing with a date field. To
list the most recently hired employees first, index on the expression
{12/31/99} - DATE__HIRED. The later the date hired is, the smaller
the time between it and the end of the century.
MAINTAINING INDEXES _
When you use the File menu popup to create a new index or open an
existing index, all other indexes are automatically closed. This might not
seem to be a problem, since you can only use records in one order, but
there is actually a reason to open many indexes simultaneously.
If you add or change data in a database, the only indexes that will
reflect the additions and changes are those that are open at the time
you make the changes. Indexes that are not open will not be updated.
There are two ways of dealing with this problem.
• You can reindex the file before you work with the indexes that
were closed when you changed the file. You do this by open¬
ing the index and then selecting Reindex from the Database
menu.
UNDERSTANDING INDEXES AND EXPRESSIONS 151
• You can use the Setup dialog box from the Database menu to
open more than one index simultaneously. One will be the
main index and the records will be displayed in the order that
it indicates, but all of the indexes will be updated each time
that you add or edit records in the database file. Up to 21
indexes may be open at one time.
CH. 4
disappears when you use the file with another index. Then, you will
use Reindex to make it reappear.
3. Now select Open from the File menu, and select a different
index—DATES.IDX—from the Open dialog box. Note
that FoxPro generates the command SET INDEX TO
DATES.IDX in the Command window.
4. Select Browse from the Database menu. The new record is
not in the Browse window, as shown in Figure 4.23, because
the current index was not open when you appended it.
▼ Command
JLAST
APPEND
SET INDEX TO DATES.IDX
BROWSE LAST
Figure 4.23: The new record is nowhere to be seen using the DATES index.
UNDERSTANDING INDEXES AND EXPRESSIONS 153
MANAGING INDEXES
USING THE SETUP DIALOG BOX
Of course, it would be tedious work to reopen each of the other
indexes individually and reindex each one separately. Instead, try
using the Setup dialog box to open all of them at once:
IJOHNSON
Levy
Address
* Command
|EX TO DATES.IDX
BROWSE LAST
REINDEX
BROWSE LAST
Database: EMPLIST
Structure: <Modiffl> Indexes: Index
R
L[ ]J Set
set Fields...
t
( ) Offl
[ 1 Fiflte
c (•) Ofif
ter... « OK »
[ J Forfla
Sat...
Figure 4.25: The Setup dialog box, with one index active.
2. Select the Add text button. The Open Index File dialog box
appears. Select NAMES.IDX from the scrollable list of
index files. It is added to the list under DATES.
4. Select Reindex from the Database menu. FoxPro talk will tell
you that it is reindexing all four of the index files that are
open.
Now you know how to open more than one index. You can do the
same thing before adding records, and all open indexes will be
updated. You will not “lose” records when you use one of these
indexes as the main index, as you did earlier. If you are skeptical, you
can try it yourself, since all the indexes are now open.
When you select one of the indexes from the list in the Setup dialog
box, the expression that it is indexed on appears to the right of the
words “Index expr:” just below the list of indexes.
UNDERSTANDING INDEXES AND EXPRESSIONS 155
Database: EMPLIST
Structure: <ModifH> Indexes: Index
►FNAME C 15 0 •DATES
LNAME C 20 0 NAMES <Modify...>
ADDRESS C 25 0 WAGES < Remove >
APT NO C 5 0 ZIPS <Set Order>
l CLEAR
SET INDEX TO C: LEARNFOX
Figure 4.26: The setup dialog box with multiple indexes open.
• Set Order: uses the index that has been selected as the main
index, which determines the order in which the fields are dis¬
played (and moves the bullet next to it in the list).
These three text buttons are very important, and you should take a
moment to try them out. Other features of the Setup dialog box will
be discussed later: the Set Fields and Filter check boxes in Chapter 5,
since they are most often used with queries, and the Format check
box in Chapter 9, when we discuss custom screens.
When you work from the dialog box, you always must use two
steps to open a file and index—generating a USE command and then
156 MASTERING FOXPRO
CH. 4
SORTING __
As you know, indexing a file changes only the apparent order of the
records, while the actual way that they are arranged in the database file
remains the same. It is possible, however, to change the actual order of
the records by choosing Sort from the Database menu.
When you sort, you create a new database file to place the sorted
records in. Sorting is rarely used in FoxPro, since it is slower and
clumsier than indexing, but you should take a moment to look at the
a Of course, it is
impossible to sort or
features of the Sort dialog box, illustrated in Figure 4.27.
The upper portion of this dialog box contains what is called a field
picker. Select the field that you want from the scrollable list labeled
index on memo fields, so
the scrollable list in the
Database Fields, on the upper left, and then select the Move text
field picker leaves out button to move it into the box labeled Sort Order, on the upper right.
memo fields. You can sort on more than one field. Add fields to the Sort Order list
in order of their importance: a field lower on this list is only used as a tie¬
breaker if all the fields higher than it are identical. For example, to sort
on the full name, you would put LNAME first and FNAME second in
the Sort Order box. The order you end up with would be the same as
if you indexed on the expression LNAME + FNAME. If you change
your mind about adding a field to the Sort Order list, you can remove it
by using the Remove text button.
The box labeled Field Options, in the center of the dialog box,
includes two radio buttons to let you sort in Ascending or Descending
UNDERSTANDING INDEXES AND EXPRESSIONS 15 7
order (with Ascending as the default) and a check box to let you
choose to ignore case (upper and lowercase). To sort in alphabetical
order by name, you should check this box in addition to moving
LNAME and FNAME to the Sort Order box.
The Database popup control on the bottom left lets you access
other databases that are open and create a sorted file that includes
fields from more than one existing file. To do this, you must be work¬
ing with a relational database and must open multiple files simultane¬
ously and relate them to each other, a relatively advanced feature of
FoxPro that you will learn about in Part II of this book. The Input
box in the bottom center includes Scope, For, and While check boxes
that let you choose which records go into the new file; similar check
boxes are used in many FoxPro dialog boxes, and you will learn
about them in the next chapter.
The Output box next to the Input box includes a Fields check box:
selecting it displays a new dialog box that lets you choose which fields
will be included in the new sorted file.
After you have chosen all of the sort options you want, you may
choose the Save As text button. The Sort Destination File dialog box
158 MASTERING FOXPRO
CH. 4
appears. Within this dialog box, enter a new name for the output file,
and then select the Save text button; or you could simply have typed
the name for the new hie in the text box under the Save As text but¬
ton. When you are finished, select the OK text button of the Sort dia¬
log box.
Rather than using the Sort dialog box, you can enter the command
SORT in the Command window. However, this is a complex com¬
mand. For a discussion of how to use this command, see Appendix C.
Using Queries
and Advanced Expressions
To create a logical expression, 165
use a relational operator to make a comparison. The relational
operators are: = for equal to, < > for not equal to, = = for
identical to, $ for included in, > for greater than, < for less
than, > = for greater than or equal to, and < = for less than or
equal to.
CH. 5
• You can find a single record that meets the criterion. Then, if
you want, you can repeat the query to see if there is a second
record that meets the criterion. This method is useful for
tasks such as looking up someone by name; and repeating the
query is useful if you get someone else with the same name
the first time you try.
• You can find all the records that meet the criterion by com¬
bining queries with commands that work with the entire
database. For example, you can build a query into the Copy
command, so that records that meet the criterion are copied
into a new file when you use that command. This method has
piany uses. For example, it can be used to produce mailing
labels for everyone who meets the criterion-—for example, for
every employee who lives in California.
This chapter will mainly deal with the first two of these methods.
You will find later in the chapter that it is easy to use the same princi¬
ples with other commands and special techniques.
USING QUERIES AND ADVANCED EXPRESSIONS 165
WORKING WITH
LOGICAL EXPRESSIONS
D in an actual applica¬
tion, of course, if
-
CH. 5
LOGICAL FUNCTIONS
Operators are not the only expression elements that give a result of
true or false. Some functions, called logical functions, will also return
.T. or .F. Though they generally are used in programming, logical
functions are sometimes handy during ordinary use of FoxPro.
One common example is the function EOF(), which stands for End
Of File. As long as the pointer is on one of the records of the file, EOF()
is false. If you are at the last record, though, and you use the command
SKIP to move the pointer to the next record, EOF() will become true, to
indicate that you are beyond the point where records exist.
EOF() also becomes true if you make a query and FoxPro does not
find what you are looking for. The pointer goes through all of the
records looking for the criterion you gave it, and passes by the last
record without finding it. To indicate this, it makes EOF() true. You
will use this function in Chapter 10 when you start programming.
RELATIONAL OPERATORS
Logical functions and operators are included in the Logical popup
control of the expression builder dialog box, shown in Figure 5.2.
Although all the operators on this popup are referred to loosely as log¬
ical operators, it is more precise to divide them into relational and
logical operators.
Relational operators are used to make comparisons. They can be
used to compare numbers, strings, or dates.
The = operator, which you glanced at earlier, is an example. You
can use expressions such as DATE_HIRED = {10/10/85} or
USING QUERIES AND AD VANCED EXPRESSIONS 167
()
<
Math String
CH. 5
the records of people who live on a street named Broadway. You can
read this expression as “ BROADWAY is contained in upper of
ADDRESS.” This operator applies only to character data; it can be
One other point you should consider, while you are at it, is that in
these comparisons, FoxPro uses the second string as the criterion and
CH. 5
compares the first string with it. In Step 1, for example, it uses
‘‘SMITH” as the criterion, and it looks through “SMITHSON” to
see that all the letters in “SMITH” are matched. Thus, it would not
find that the reverse, “SMITH” = “SMITHSON”, is true: when
it looks at “SMITH”, it would not find that all the letters in
“SMITHSON” are matched. Try this out by entering ? “SMITH”
= “SMITHSON”. FoxPro evaluates the expression and prints .F.
This example shows why actual queries have the form LNAME =
“SMITH” rather than “SMITH” = LNAME. For the same rea¬
son, you can find all the names that begin with the letter A by using
the criterion UPPER(LNAME) = “A”.
LOGICAL OPERATORS
Though the relational operators that were listed in Table 5.1 are
loosely referred to as logical operators, this section will look at the logi¬
cal operators in the stricter sense of the term. These operators, used
to create more complex expressions, are shown in Table 5.2.
Operator Meaning
would be used to narrow the query so that it finds only some of the
employees from California: those with wages less than $10.
172 MASTERING FOXPRO
CH. 5
If you find these STATE = “CA” could be used to find the records for all the states
operators confusing, except California; that is, it would find every record that is left out by
you should add the words
“it is true that” when
the expression STATE = “CA”. You simply have to remember to
you read the expressions use .NOT. before the entire logical expression it refers to.
to yourself. Read
STATE =“CA” .OR.
STATE = “NY” as “it is USING PARENTHESES FOR COMPLEX EXPRESSIONS
true that the STATE
equals CA or it is true You can combine complex logical expressions with .AND. and
that the STATE equals .OR. indefinitely, creating more and more complex expressions.
NY,” and you will not
When expressions contain more than one of these operators, it is best
confuse the .AND. with
the .OR. operator. Like¬
to group them using parentheses to indicate precedence.
wise, .NOT. is some¬ For example, let’s say that you want to find employees from Cali¬
times clearer if you read fornia and from New York who earn less than average wages for the
it as “it is not true that.”
area. You know that the average wage in California is $10 and that
Thus, it is probably best
to read .NOT. STATE the average wage in New York is $11.
= “CA” as “it is not true To find the records from California, you would use the expression
that the STATE
equals CA.”
STATE = "CA" .AND. WAGE < 10
To find the records from New York, you would use the expression
Then, to find all the records you want, you would combine these two
with .OR. to get
(STATE = "CA" .AND. WAGE < 10) .OR. (STATE = "NY" .AND.
WAGE < 11)
ORDER OF PRECEDENCE
In Chapter 4, you saw that if you leave out parentheses, numeric
expressions are evaluated in default algebraic order. In fact, all Fox¬
Pro expressions are evaluated in the following order of precedence if
you leave out parentheses.
1. exponentiation
6. .NOT.
7. .AND.
8. .OR.
CH. 5
There are also cases where an index is not useful. If all of your
employees lived in two states, for example, it would be foolish to use
an index to search for state names. The program would have to read
through about half the file anyway just to read all the records with the
state you wanted, so using an index would not save much time. In
this case, maintaining an index is more trouble than it is worth.
Likewise, there is no need to use an index to produce a report if
you plan to go do something else while the report is being printed. If
time is not a concern, there is no reason to go to the trouble of main¬
taining an index.
Figure 5.5: A dialog box with For, While, Scope, and Fields check boxes.
The Scope and Fields check boxes that are grouped with the For
and While check boxes in this dialog box are useful for refining que¬
ries, but they involve side issues that are not essential. They will be
covered later in this chapter.
CH. 5
index, so the names are already in alphabetical order. Then you must
put the pointer on the first record that begins with L. Only then can
you use a command containing this WHILE clause. When you use
a WHILE clause, FoxPro begins by looking at the current record
(where the pointer is) to see if it meets the criterion. If it is, then Fox¬
Pro looks at the next record and sees if it meets the criterion. It con¬
tinues to look at records in this manner until it finds a record that
does not meet the criterion, at which point it stops the search.
Think about the pitfalls this process involves—since they some¬
times come up and it will be helpful if you can recognize the disease
when you see the symptom:
None of these problems can occur when you use a FOR clause,
which automatically begins at the first record and reads through the
entire file, and so it is best to use a FOR clause when possible.
There are cases, though, when you are working with large files,
when the extra speed of a WHILE clause makes all the trouble
worthwhile. In addition, WHILE clauses are particularly useful in
programming, since all the preliminaries are done automatically by
the program. There is also a short-cut command for putting the
pointer on the first applicable record before using a WHILE clause,
which you will learn in the next section.
USING QUERIES AND ADVANCED EXPRESSIONS 177
As you have seen, you can use queries to find either a single record
or all records that match a certain criterion. In either case, you can
decide to do either an indexed or an unindexed search.
[ ] Scope...
« Locate »
[ ] |or...
< Cancel >
[ ] jjjhile.
H Though it is pos¬
sible to use both a
Figure 5.6: The Locate dialog box.
As you can see, the Locate dialog box has a For, a While, and a
FOR and a WHILE
clause in a command in Scope check box. Many dialog boxes have these three check boxes
this way, it is confusing together, but in this case, arranging them this way is a bit misleading,
and should be avoided. If
since they are not parallel options here, as they usually are. LOCATE
you do use both, the
WHILE clause takes must have a FOR clause; the WHILE and SCOPE clauses are
precedence. optional and merely limit the number of records that FoxPro
178 MASTERING FOXPRO
CH. 5
searches through. (When you look at Scope at the end of this chapter,
you will see that it merely lets you specify that some command be car¬
ried out on the next 10, 20, or whatever number of records you
choose. The While option can also be used in combination with FOR
to carry out the LOCATE FOR command only for as long as the
WHILE condition is true.
The basic way of using the Locate dialog box, then, is by checking
the For check box. When you do so, the expression builder will
appear, so you can enter the logical expression that you will be using
as the criterion for your search. For example, to find the record for
somebody named Johnson, you would enter the expression
UPPER(LNAME) = “JOHNSON”.
LOCATE FOR will begin with the first record in the database file
and read through it sequentially until it finds a match, regardless of
where the pointer is when you begin—the same way that FOR
clauses normally work. If it does not find any record that matches,
FoxPro “talk” will display a message saying “End of Locate
Scope. ’ ’ In addition, the pointer will be set at the end of the file posi¬
tion, so that the function EOFQ is true.
If LOCATE FOR finds the record you want, but you also want to
see the next record that meets the criterion, select Continue from the
Record menu (or use the command CONTINUE).
Try these two commands, which you are bound to use frequently
for the everyday work of looking up records:
1. Select Open from the File menu, and when the Open dialog
box appears, select EMPLIST.DBF. In order to see the
pointer being moved by the commands, open the Browse
window by selecting Browse (from the Database menu
popup).
Select LNAME from the Field Names list. Then select the
Logical popup control, and select = from the list that pops
up. Select the String popup control again, and select “text”
from the list that pops up. Type JOHNSON in the quotation
marks that have appeared. This gives you the complete
expression you want, as shown in Figure 5.7. (Alternately,
you simply could have typed the expression UPPER
(LNAME) = “JOHNSON”.)
CH. 5
f Command
MiQ HjH” = "SMITHSON"
USE EMPLIST.DBF
BROWSE LAST
LOCATE ALL FOR UPPER(emp
y Command
fill 1ST. DBF
BROWSE LAST
LOCATE ALL FOR UPPER(emp
CONTINUE
Figure 5.9: Using CONTINUE to find the next record with the same value
USING QUERIES AND AD VANCED EXPRESSIONS 181
CH. 5
To do a seek using the menu system, select Seek from the Record
menu, and FoxPro will display the expression builder so you can
enter the expression that matches the main index. As you will see, the
expression builder reminds you that you do not have to enter
the entire logical expression that is your criterion. You just enter the
second half of the expression, which FoxPro assumes you want to
match with the fields in the main index. Try it:
1. Select Open from the File menu popup. When the Open dia¬
log box appears, select the Type popup control and select
Index from the list that appears. Then select NAMES.IDX
from the list of indexes. The names in the Browse window are
now listed alphabetically.
The example above shows that SEEK does an indexed search of the
entire database: it does not just begin where the pointer is.
When you are entering the criterion for the SEEK command, think
carefully about the exact expression that the index uses. At first, it
might seem puzzling that SEEK seemed to ignore capitalization when
it found “LEVY”. Remember, though, that SEEK was searching
using the main index, thus, the expression UPPER(LNAME) +
UPPER(FNAME). The index expression capitalized the LNAME
field; thus, it did match the criterion “LEVY”.
USING QUERIES AND ADVANCED EXPRESSIONS 183
If you want to find After you have done a SEEK in this way, the index is still open as
the next single
record that meets the
the main index, and the pointer is on the first record with the value
criterion after you have you want. This leaves you all ready to use a command with a
used a SEEK, all you WHILE clause.
need to do is look at the
next record in the Browse
window. Since this is a
search on the key field of QUERIES FOR MULTIPLE RECORDS
the index, the next record
that matches the criterion
When you query for all the records in a file that match the crite¬
(if there is one) is simply rion, many database management programs automatically put the
the next record in the file. results of a query in a new database file, which they call the Answer
file or something similar. Then, if you want a report or mailing labels
that contain only the records that match the query, you must produce
the report or labels using the Answer file.
FoxPro and other dBASE compatible programs do not require
you to go through this unwieldy process. You can add a FOR or a
WHILE clause to many commands—including the commands that
you use to produce reports or labels—and, in essence, build the
query into the command.
As an exercise to learn how to use the FOR and WHILE clauses,
you will make a query that works like a conventional query that puts
184 MASTERING FOXPRO
CH. 5
all the matching records into a new file. There are times when you
need to make this sort of simple query. It is very easy to do this using
FoxPro by selecting Copy To from the Database menu and checking
For or While in its dialog box—or by using the COPY command with
a FOR or WHILE clause—to copy the records that match the crite¬
rion into a new file. You can even name the new file ANSWER.DBF
if you want.
You have already learned how to make queries using LOCATE
and SEEK for a single matching record. By using COPY with FOR
and WHILE clauses, you will get a general idea of how to make que¬
ries for all the matching records in a file—so that you will also be able
to use FOR and WHILE with other menu choices or commands.
2. Select STATE from the list of field names. Select the Logical
popup control and select = from the popup that appears.
Then select the String popup control and select “text” from
the popup that appears. Type CA in the quotation marks.
Select the default text button OK to confirm the expression
and return to the Copy To dialog box.
3. Type ANSWER1 in the text box under the Save As text but¬
ton. This will be the file containing all the records that match
your STATE = “CA” criterion. The dialog box should now
look like Figure 5.11. Select OK to copy.
4. Select Open from the File menu. When the Open dialog box
appears, use the Type popup control to select Database.
Then select ANSWER 1 .DBF from the scrollable list of files.
Select Browse from the Database menu to view it. Scroll until
you can see the State field, and you will see that all the
records are from California. Then close the Browse window.
USING QUERIES AND ADVANCED EXPRESSIONS 185
In general, if you are working from the Command window, you can
copy the database file that is currently open simply by using the
command
and the file name does not have to include the .DBF extension. To
build a query into the command by adding a FOR clause, you could
simply enter
CH. 5
Even though this database hie is not indexed on the State held, you
can use a WHILE clause with it if you remember that California resi¬
dents have zip codes beginning with a 9. You will use the ZIPS index
you created and use the criterion Zip = “9” to copy all the California
records. Notice how convenient it is that Zip code is a character held and
matches the criterion even if there are other characters after the 9.
1. Select Open from the File menu. When the Open dialog box
appears, select EMPLIST.DBF from the list of hies. Select
Browse from the Database menu (though it is not necessary)
so you can see what you are doing.
%
2. Select Open again from the File menu. When the Open dia¬
log box appears, use the Type popup control to select Index.
Then select ZIPS.IDX from the list of hie names. Scroll right
until you can see the State and the Zip fields.
3. Select Seek from the Record menu. Type “9” in the text box
as the character expression to seek. (Do not forget to include
the quotation marks.) Then select OK. The pointer moves
to the first California record, as shown in Figure 5.12.
▼ Command
QOL1ST.DBF
BROWSE LAST
SET INDEX TO ZIPS.IDX
SEEK "9"
6. To see the result, select Open from the File menu. When the
Open dialog box appears, use the Type popup control
to select Database. Then use the list of files to select
ANSWER2.DBF. Select Browse from the Database menu
and scroll right until you can see the State and Zip fields.
Notice that the file has the same records as the ANSWER 1 file but
that they are in zip code order. Even though this file is not indexed,
that is the order in which you copied the records.
If you were working from the command line, you would have
entered
then
SEEK "9"
and then
You can see that it is not worth going through the extra effort of
using WHILE with a database file as small as this one: the time you
save is not noticeable. With a file that has a thousand records,
though, the difference in speed is definitely worth the effort, and even
the smallest businesses often have mailing lists or other files that are
this long.
188 MASTERING FOXPRO
CH. 5
As you can see, the ANSWER3 file has no records in it. The cur¬
rent record did not meet the criterion of the WHILE clause, so Fox¬
Pro did not go any further. You may now close the Browse windows.
In Chapter 2, you learned the COPY STRUCTURE command,
which you used from the Command window to create a new database
with the same structure as an existing one. What you just did is
equivalent to copying the structure.
To trick FoxPro into copying the structure using the menu system,
just use COPY TO with some untrue criterion. Using an impossible
criterion, such as WHILE 1=2, ensures that FoxPro will not copy
any records.
But there is an even easier way of doing it. Remember that when
FoxPro uses a WHILE clause, it performs whatever you have
instructed it to do until it reaches a record for which it evaluates the
logical expression as .F.. You can save it the trouble of doing the eval¬
uation by simply entering .F. as the logical expression of the WHILE
clause to begin with.
There is no need to index when you do this. The index is used with
WHILE just to make sure that all the matching records are found, a
consideration which does not apply in this case.
USING QUERIES AND AD VANCED EXPRESSIONS 189
Figure 5.13: FoxPro has been tricked into copying just the structure.
Of course, you can do the same thing from the menu system by
repeating all the steps you used in the previous examples but entering
.F. in the expression builder text box: you can type it in or select it
from the Logical popup.
CH. 5
these data types. The = operator is used most commonly when you
are searching character fields, and the >, <, > = , and < = opera¬
tors are most common when you are searching numeric fields. It will
take an extra moment, though, to look at how to search memo and
logical fields.
The 4‘included-in” operator, $, can be used for character fields,
but is most commonly used to find a substring in a memo. In the next
exercise, for example, you will look for employees who are connected
with the Christmas fund-raising drive. The only trick to this query is
figuring out all the different ways you might have entered the data in
the memo field. You need to search for both XMAS and CHRIST¬
MAS in both upper and lower case. Even then, you should read each
memo individually, since one says that the employee cannot help with
the fund raising.
When you are basing a query on a logical field, you do not need to
use a logical expression. You may recall that logical expressions are
evaluated as true or false. The content of a logical field, however, is
already one of these values (.T. or .F.). Thus, to find all the people in
the EMPLIST database who are on probation, you can use a query
with FOR followed by the logical field PROBATION. FoxPro will
evaluate this logical field just as it would evaluate any logical expres¬
sion: as true or false. Likewise, you could use the criterion FOR
.NOT. PROBATION to find the records of employees who have .F.
in the field.
The following exercise will used unindexed queries, using COPY
with a FOR clause, though you could just as well use LOCATE FOR
and CONTINUE.
1. Select Copy To from the Database menu, and select Save As.
Type ANSWER5 in the text box, next to Save As, as the
name of the file to copy to, and select the For check box. In
the expression builder, type
"XMA
3. Again select Open from the File menu popup and select
EMPLIST.DBF from the scrollable list of file names. Select
Copy To from the Database menu. Type ANSWER6 in the
text box near Save As. Then select the For check box. When
the expression builder appears, select the field PROBA¬
TION from the scrollable list of field names: this field name
will complete the FOR clause in the expression builder.
Select OK to use this expression, and select OK to execute
the command.
4. Select Open from the File menu once more and select
ANSWER6.DBF from the scrollable list of file names. Select
Browse from the Database menu popup to view the file.
Scroll to see the Probation field and confirm that all of them
are .T., as shown in Figure 5.15. Close the Browse window.
192 MASTERING FOXPRO
CH. 5
▼ Command
When you were looking at the memo fields, you might have
noticed that fund raising was spelled in three ways: fund raising,
fund-raising, and FUNDRAISING. This gives you an idea of what
you are up against when you are searching memo fields.
in order to make a query that is similar to the first one you made in
this section but that leaves out deleted records.
You can access DELETEDQ through the logical popup of the
expression builder, so you can also generate this function by working
with the menu system.
As you can see, there are many ways of accomplishing the same
task when you are using FoxPro. The dBASE compatible language
gradually grew, with more commands and functions to let you do
things more conveniently. There is no need to learn all of the com¬
mands and functions—since many of them just do the same things in
different ways that different users prefer. You should just be aware of
them and learn the ones that let you do what you want in a way that is
easiest for you.
194 MASTERING FOXPRO
CH. 5
SPECIAL TECHNIQUES -
You have learned the basic techniques for making queries to find
either one record or all the records that match a criterion:
These techniques are the workhorses that you will constantly use
when you are working with FoxPro.
FoxPro also provides two special techniques that you might find
make your job much easier on occasion. Both of these are similar to
what you have already learned, and it should be easy for you to pick
them up at this point.
SETTING A FILTER
There are often times when you want to perform a long series of
commands, all of which apply only to records that meet some crite¬
rion. Obviously, it would be unwieldy to use the For check box or a
FOR clause with each of these commands separately. For this rea¬
son, FoxPro also gives you the option of setting a filter.
After you set a filter, you do not need to worry about adding the
criterion to each command. Records that do not meet your criterion
are filtered out indefinitely, until you remove the filter.
Using the menu system, you can set a filter by selecting Setup from
the Database menu popup. Then use the Filter check box of the
Setup dialog box, which lets you enter a criterion in the expression
builder. After you do this, only those records that match the criterion
will be used with commands you select. The filter will continue to be
active until you remove the check from the check box.
USING QUERIES AND AD VANCED EXPRESSIONS 195
2. Select Setup from the Database menu. When the Setup dia¬
log box appears, select the Filter check box. The expression
builder appears, with SET FILTER Expression: <expL>
over the text box. Type STATE = “CA” in the text box (or
use the expression builder to create the same expression).
Then select OK.
4. Select Browse from the Database menu. Since the filter has
been set, only the California records are visible. Only they
will be used with any command.
Database: EMPLIST
Structure: <ModJLffl> Indexes: Index
CLEAR
USE EMPLIST.DBF
SET FILTER TO STATE = "C
CH. 5
5. Select Setup from the Database menu and select the Fil¬
ter check box again. The expression builder appears, with
STATE = “CA” entered as the expression in its text box.
Press Del to delete the expression. Then select OK to return
to the Setup dialog box. The check in the Filter check box dis¬
appears, and the command SET FILTER TO is generated in
the Command window. Select OK, and you can see all the
records in the Browse window again. Close the Browse
window.
following example, then, you will use the For check box to see how
powerful a query built into an index is.
1. Select New from the File menu. From the New dialog box,
select the Index radio button. Then select OK.
UPPER(LNAME) + UPPER(FNAME)
(Or you could select the Expr text button and use the expres¬
sion builder to create this same expression.)
INDEX ON:
►FNAME C
LNAME C
ADDRESS C « OK »
APT_NO C
CITY C < Cancel >
STATE C
[ ] Unique
HZMHB3 STATE - "CA"
CH. 5
and select OK. Note that the command generated is like the
usual INDEX command plus the usual FOR clause:
5. Select Setup from the Database menu. Select the Add text
button four times in order to add each of the four indexes to
the index list. Then select the NAMES index from the
Indexes list, and select the Set Order text button to make this
the main index. The Setup dialog box should now look like
Figure 5.18. Select OK.
Database: EMPLIST
Structure: <Modiffl> Indexes: Index
E i Mi
' ‘ ob (•) Oflf
I
iter.. . « OK »
lat. . .
SET FILTER TO
INDEX ON UPPER(LNAME) +
SETINDEXH^^UIARNKIX
Figure 5.18: Setting up the database to add data with all indexes active.
6. Select Browse from the Database menu. You now can see all
the records in the Browse window in alphabetical order.
Select Append Record twice (from the Browse popup) in
order to enter these two new employees:
Despite its power, the query built into an index obviously is not
useful for every purpose. You have to weigh the time saved by build¬
ing the query into an index against the time lost by having to main¬
tain the index. Using this sort of query is worthwhile if you are
working with a large file and need to make the query frequently.
CH. 5
SCOPE
Scope merely refers to the number of records that FoxPro searches
in the course of performing a command. Many commands can be
used with Scope clauses: they do not necessarily have any inherent
relation to FOR and WFIILE clauses.
Appendix C, your reference book of Commands and Functions, or the
listings in the Help window can tell you which commands can be
used with Scope clauses and where they must be placed if other
clauses are also used. Descriptions of these commands include the
word [scope] to indicate where a Scope clause goes, with the square
brackets indicating that it is optional. The word scope, though, is not
actually used in the clause. Instead, Scope clauses consist of any of
the following words:
| One other minor Now you can see that the main difference between these commands is
■■I difference between their default scope. DISPLAY ALL is virtually identical to LIST, and
the two is that DISPLAY
ALL will display records
LIST NEXT 1 is virtually identical to DISPLAY (though there are a
one screen at a time, couple of other, very minor, differences apart from their scope).
pausing and asking you To see how to use these options through the menu system, by
to press any key to see the
using a Scope check box, you will try deleting all of your records.
next screen. This
difference makes DIS¬ Don’t worry—remember that this command just marks records for
PLAY ALL the easiest deletion, and you can use Recall with a Scope check box to get them
way of scrolling through
all back.
data to view it on the
screen if you are working
from the Command 1. If you want to clear the screen, enter CLEAR. Select Delete
window. from the Record menu. When the Delete dialog box appears,
select the Scope check box. When the Scope dialog box
appears, as shown in Figure 5.19, select the All radio button.
Then select OK to return to the Delete dialog box, and select
Delete. Notice that the command DELETE ALL has been
generated. Select Browse from the Database menu, and note
that all the records have bullets to their left to indicate that
they are marked for deletion.
Scope:
« OK »
CH. 5
2. Select Recall from the Record menu. When the Recall dialog
box appears, select the Scope check box. When the Scope
dialog box appears, select the All radio button. Then select
OK to return to the Recall dialog box and select Recall. If
you check the Browse window at this point, you will notice
that the command RECALL ALL is generated and that all
the bullets have disappeared to indicate that the records are
no longer marked for deletion. Close the Browse window.
When you first used the Scope check box with either Delete or
Recall, the Next radio button was chosen and the default scope 1 was
written to its right. Because this is the default scope of the command,
just the current record is deleted or recalled if you do not use the
Scope check box at all.
FIELDS
Just as you can use a command with a Scope clause to restrict the
records that the command applies to, you can also use a command
with a FIELDS clause to restrict the fields that it applies to. You
should check Appendix C, your Commands and Functions reference, or
the Help window to see where the fields list fits into the syntax of any
given command.
You can use a
Unlike a Scope clause, which cannot contain the word scope, a
FIELDS clause with
expressions instead of just
FIELDS clause can either contain the word FIELDS followed by
with field names in order a list of fields (or expressions) or it can simply contain the list of fields
to make the output look (or expressions). In either case, commas must be included between
better. For example, in
each of the fields or expressions in the list. Some commands require the
the next exercise, you will
use PKOPER(TRIM . word FIELDS. To avoid confusion, it is best to always use the word
(FNAME) + “ ” + LNAME) FIELDS if you are working from the Command window.
to get a better-looking
Like a scope, a fields list can be combined with many commands
listing than you would get
with just FNAME, LNAME. and can also be used in conjunction with FOR or WHILE clauses.
For example, try using Copy to create a new file that has only the
names and addresses of the employees who live in California.
2. When the Copy dialog box appears, select the For check box. In
the text box of the expression builder, enter STATE
= “CA” (or use the expression builder to create this expres¬
sion). Then select OK to return to the Copy dialog box.
3. Select the Fields check box. FoxPro displays the field picker
dialog box shown in Figure 5.20. Select the FNAME,
LNAME, ADDRESS, APT_NO, CITY, STATE, and
ZIP fields from the scrollable list of fields to move them to the
Selected Fields list. Then select OK to return to the Copy
dialog box. Enter ANSWER7 in the text box near Save As
and select OK to copy the file.
Database:
<Cancel >
EMPLIST
« OK »
Figure 5.20: The field picker dialog box called by selecting the Fields check box.
4. Select Open from the File menu, and select ANSWER7 from
the list of files in the Open dialog box. Select Browse from the
Database menu to look at the new file. Scroll right to see that
it includes only the fields you listed and only the records from
California. Close the Browse window.
CH. 5
The DOS command Then enter RUN DEL ANSWER?. * to use DOS to delete all
uses two wild-card these hies.
characters. ? stands for
any single character; it
makes the command
Many menu selections include only For, While, and Scope check
include all the files with boxes in their dialog boxes, and leave out the Fields check box. If you
numbers following the are working with these menu choices, you can still restrict the fields
word ANSWER. *
they apply to by using the Setup dialog box first.
stands for any word; it
makes the command You can set fields in much the same way that you set a filter. You
include the memo files use the Filter check box of the Setup dialog box to set a filter that
with .FPT extensions as
works just like having a FOR clause in a command. Likewise, you
well as the database files
with .DBF extensions. can use the Set Fields check box of the Setup dialog box in the same
way. It works just like having a FIELDS clause in a command—with
one difference: the Set Fields check box has On and Off radio buttons
under it. This allows you to turn off the fields setting temporarily and
then turn it on again without going through the bother of choos¬
ing the fields again.
You can do the same thing working from the Command window
by using the command SET FIELDS TO Kfield names >. This com¬
mand is used together with the commands SET FIELDS OFF and
SET FIELDS ON, which temporarily suspend and reactivate the
field setting you have chosen. The command SET FIELDS TO ALL
will make all of the fields in the current database active.
Since you can use expressions as part of the field list, you can even
include calculated fields in the report. Try, for example, getting an
alphabetical listing of the names and wages of your employees who
live in California, and add a calculated field, using the expression
40 * WAGE to calculate basic weekly wages (assuming that all em¬
ployees work a base 40-hour week).
Remember that the
OFF used with the
1. Enter CLEAR, then enter USE EMPLIST INDEX NAMES
LIST command simply
makes the command 2. Enter
leave out the record
numbers, which you do LIST FIELDS LNAME, FNAME, WAGE, 40*WAGE FOR STATE =
not want in an alphabeti¬ "CA" OFF
cal listing. OFF usually
comes at the end of a 3. To make the listing look nicer, you can combine the first and
LIST command—only last names, so the listing has a single name column. Enter
TO PRINT and TO '
FILE can come after it— LIST FIELDS PROPER(TRIM(FNAME) + " " + (LNAME)),
so, to avoid confusion, WAGE, 40*WAGE FOR STATE = "CA" OFF
you must remember that
it has nothing to do with
the preceding clauses. If the listing on the screen, shown in Figure 5.21, looks good to
you, you can add TO PRINT at the very end of the command in
order to get a quick printout of the data you need.
Command
CLEAR
USE EMPLIST INDEX NAMES
LIST FIELDS LNAME, FNAME
LIST FIELDS PROPER(TRIM(
CH. 5
Do not use propor¬ If you want a report that includes page breaks, page headers and
tional fonts when footers, and the like, you can add TO FILE Kfile name> after OFF to
you print the data of a
save the output of the report in a plain ASCII text file. Most word
text file generated by Fox¬
Pro. Remember that processors can import ASCII hies (some call them DOS text hies)
FoxPro pads out the and they can add any formatting you want to the data. You can
space between columns
change the headings above the columns and even use a variety of
by using the blank char¬
acter. Proportional fonts fonts if your word processor supports them.
use less space for blanks You can see now how worthwhile it is to know about FoxPro
than for other characters,
commands—and about the different types of expressions and clauses
so that they will not align
the columns properly. Of that can be used with many of them. Though they have taken you a
course, you can use bit of extra time to learn, the extra power that they give you will more
proportional fonts to add than repay you for the trouble. As you have just seen, a one-line com¬
a report title.
mand can produce an entire report for you.
Of course, there are also times when you want reports with more
sophisticated features—-for example, reports that group your data to
make it easier for you to analyze. For these, you can use the FoxPro
report generator, which you will learn about in the next chapter.
WBBSB
Generating
Reports and Mailing Labels
■MM
Creating a report
is a two-step process. First design the report form: either enter
the command CREATE REPORT Kfile name'> or select New
from the File menu and select the Report radio button to design
the report using the report layout window. After the report
form is designed, select Report from the Database menu to call
up the Report dialog box, which lets you print the actual
report. The Form text button in this dialog box lets you choose
among report forms you have already designed.
To group data,
select Data Grouping from the Report menu to call up the
Group dialog box, which lets you add, change, or delete a
grouping. When you add a grouping, the Group Info dialog
box appears, to let you specify the field or expression on which
the data is grouped. When you are done, bands appear for the
header and footer of the group. You must also index correctly in
order for the final report to be grouped properly.
To add a field expression to the report, 226
select Field from the Report menu to call up the Report Expres¬
sion dialog box. Then select a field name from the scrollable
list, or type an expression in the text box, or select the Expr text
button to use the expression builder to create the expression.
CH. 6
CREATING REPORTS _
There are two steps to creating FoxPro reports. First, you must
design the report form. Then you can actually produce the report.
The report form determines how field data, text, and graphics are
laid out, and also lets you group and summarize data.
You create a new report form in the same way you create a new
database file or a new index: simply select New from the File menu
and then select the Report radio button. This command lets you use
the report layout window, shown in Figure 6.1. As usual, FoxPro
names the report form Untitled until you select Save As from the File
menu to save it and give it a name. (If you are working from the
Command window, you can enter the command CREATE REPORT
to use the report layout window in this way. Alternately, you can
enter CREATE REPORT Kfile namey to name the report from the
beginning.)
GENERATING REPOR TS AND MAILING LABELS 213
Before you can create a report, a database file must be open. You
should also open the index you want to use for the report. (As you will
see later, you can save the report’s “environment” so that the index
is opened automatically when you want to produce the report.)
As you can see from the illustration, a Report menu pad is added
to the menu bar when you are using the report layout window. You
can see that the report is divided into bands: you can use the menu to
add expressions or graphic characters in any of these bands, and you
can simply type text into them.
Also notice the status line at the top of the window. The numbers at
the left, next to R and C, tell you the Row and Column of the cursor
location. The word to the right of that tells you what action is currendy
being performed, such as moving the cursor, drawing a box, or defining
a held. The final item of the status line tells you the band where the cur¬
sor is located.
The report layout window will be discussed in detail in the next
section.
When you have finished designing the report and save it, FoxPro
adds the extension .FRX to the name you give the report. If you save
the environment also, FoxPro gives the extension .FRV (which
stands for FoxReport View) to the file where it is saved.
214 MASTERING FOXPRO
CH. 6
DBASE, FoxBase, You can modify an existing report form, also, in the obvious way.
and other earlier
You selected New from the File menu popup to create a report form;
dBASE compatible pro¬
grams saved report forms
now you select Open to modify one. After selecting Open, you would
with the extension .FRM. select the Report radio button, and select from the scrollable list the
If you are running older name of the report form you want to modify. (From the Command
applications on FoxPro, it
window, simply enter MODIFY REPORT Kfile name >.)
will be able to use these
.FRM reports without Once you have designed and saved the report form that you want,
any trouble, and will you can use it at any time to produce actual reports. To do this, you
include them in the list of
select Report from the Database menu, and FoxPro displays the
report forms for you to
choose from. The one Report dialog box shown in Figure 6.2.
possible confusion arises
if you are working from
the command line, where
you can enter the report’s -System tile Edit Database Record Program Window
To determine which report form is used, you can either type the
name of any existing report form for the current database into
the text box, or select the Form text button to choose from a list of all the
reports for the current database. As you can see from the figure, this dia¬
log box includes an Environment check box. If you saved the environ¬
ment when you created the report form, checking this option will
automatically open the index you need and set the other environmental
variables that you saved in the .FRV file.
This dialog box also includes Scope, For, and While check boxes,
so that you can select which records to include in the report. If you
GENERATING REPOR TS AND MAILING LABELS 215
have designed a report form that lists employee names and addresses,
for example, you can use the For check box to print out the report
with only the employees from California, only the employees who
earn more than a certain wage, or whatever.
The dialog box also includes a set of check boxes that let you
choose these printing options:
• Plain: prints the report with a page header only on the first
page, and suppresses headers on following pages.
Reports will be Finally, this dialog box also has check boxes that let you decide
printed or sent to a whether to send the report to the printer or to a text file on disk. The
text file more quickly if
you select the Console Off
Console On and Console Off radio buttons next to these check boxes
radio button. Remember determine whether the report is displayed on the screen while it is
also that the command to produced. If the Console On radio button is selected and neither To
produce a report, like
Print nor To File is checked, the report is simply displayed on the
most commands, is inter¬
rupted if you press Esc— screen.
a feature that is often To produce a report from the Command window, enter REPORT
useful when you are
FORM <Lfil,e namey to produce a report. The most important options
producing a report on
large databases.
with this command are a FOR or WHILE clause to determine which
records are printed, which can be followed by TO PRINT or TO
FILE Kfile name> to send the output to the printer or a text file
respectively. (See Appendix C for all the options that can be used
with this command.)
This discussion has given you a general idea of the two-step process of
creating reports: designing the report form and then producing the
report. Now we will look in detail at how to design a report form.
216 MASTERING FOXPRO
CH. 6
You can choose to have your titles and summaries on pages sepa¬
rate from the rest of the report. Groupings can also begin at whatever
point they naturally occur or, if you choose, on a new page. You can
also use the menu to add or remove lines for each band. Bands may
be any number of lines, but the entire report form may have no more
than a total of 255 lines for all the bands combined.
Any of the bands can include
• text that you simply type anywhere on the form and which
you can edit by using the Report menu
GENERATING REPOR TS AND MAILING LABELS 217
• lines or boxes, which you add using the Report menu. These
simple graphics are created using the line characters that are
part of the extended DOS character set. They can be used to
make the report look more attractive and to highlight impor¬
tant data.
The Report menu also lets you preview the page, that is, to see on
the screen what the printed report will look like. If you are not
satisfied with the layout you created, it is very easy to change it.
Anything that you enter in the report layout window is an object. A
block of text becomes an object when you press Enter or reach the
end of a line. Before you press Enter, you can edit the text in the ordi¬
nary way. After you press Enter, it can be selected and manipulated,
but can be edited only by selecting the Text option from the Report
menu popup. Fields and expressions, lines and boxes, and even
words or lines of text are all treated as objects, which you can select
and then move or delete using either a mouse or the keyboard, in the
ways described below.
CH. 6
PAGE LAYOUT
If you select Page Layout from the Report menu, you can use the
Page Layout dialog box shown in Figure 6.4 to set margins, page
length, and the like.
Page Length determines how many lines will be printed on a single
page. FoxPro subtracts the number of lines for the top and bottom
margins from the total number of lines on the page to determine how
many lines to print. The default Page Length setting of 66 lines is
what almost all printers print on ordinary 8V2-by-l 1-inch paper.
Change this setting only if you are using some unusual paper (such as
legal-size paper) or have a printer that does not print the standard
66 lines per page.
GENERATING REPORTS AND MAILING LABELS 219
CH. 6
PAGE PREVIEW
If you select Page Preview from the Record menu you can see on
the screen how the report will look when it is printed out. Page Pre¬
view does not display type styles, such as bold, underline, or italic,
but it does include text, field expressions, lines, and boxes, just as
they will appear in the printed report.
If your report is wider than your screen, you can scroll right and
left to see the entire width of the report. At the bottom of the Page
Preview window is a status line which tells you the column where the
cursor is and also includes two text buttons—Done and More.
You can go through the report a screen at a time by selecting
More, or select Done at any time to stop previewing the report.
GENERATING REPORTS AND MAILING LABELS 221
DATA GROUPING
Selecting Data Grouping from the Report menu popup lets you
group data. A grouped report might, for example, print the data for
each state separately, and it could include a header and footer
for each state. Often the group footer includes a calculated field that
summarizes the data in the group.
When you add a grouping, new bands appear in the report layout
window to hold the group header and group footer. You can work
with these bands in the same way you work with any other bands.
Selecting Data Grouping calls up the Group dialog box, shown in
Figure 6.5. As you can see, this dialog box lets you add, change, or
delete a grouping. The scrollable list on the left represents groups that
have already been added; you can select a group from the list to
change or delete. This list can include up to 20 levels of groupings.
For example, you can group by state, by city within each state, and
so on. In the illustration, records have been grouped by state; within
each state, they are grouped by city; and within each city, they are
grouped by zip code. Notice how the bands for these groupings
are placed in the report layout window (still visible on the left behind
the dialog box).
CH. 6
Apart from this basic feature, the Group Info dialog gives you a
few optional check boxes:
• Swap Page Footer: makes the group footer appear on the last
page of each group instead of the ordinary page footer.
The New Page check box is automatically selected when Swap Page
Header or Swap Page Footer is selected, since these can only be used
if each new group begins on a new page.
There one important precaution that you must remember if you
use data groupings: you must index your data properly to make sure
that the data is grouped correctly. If you group on State without
indexing, for example, FoxPro will print a new group footer and
header each time it comes to a record where the state is not the same
as it was in the previous record. The options on the menu system just
make the report print the previous group’s footer and the new
group’s header whenever there is a change in the data in the expres¬
sion that you are grouping on.
What if you want to group by state but you also want the names of the
employees within each state to be alphabetized? You have to index on
UPPER(STATE + LNAME +FNAME) or on some equivalent
expression. The index itself must put the records in the right order for
the grouping.
TITLE/SUMMARY
Selecting Title/Summary from the Report menu displays the
Title/Summary dialog box shown in Figure 6.7, which lets you add a
title or summary to the report.
As you can see from the illustration, there are two check boxes
under both Report Title and Report Summary. Checking the first
adds a title band or summary band to the report layout window. You
can work in these bands in the same way that you work in other
bands. Checking the second check box in each pair makes FoxPro
print out the report title or report summary on a separate page.
You might want to use the tide band not just for a one- or two-line
title but for an abstract of the report. Similarly, you could use it for a
cover letter to each person who gets the report. This is one case where
you would want it to appear on a separate page.
Of course, the title actually appears below the header of the first
page, even though the title band is above the page header band. Simi¬
larly, Summary actually appears above the footer of the last page,
even though its band is below the page footer band.
224 MASTERING FOXPRO
CH. 6
BOX
After you select Box from the Report menu, the word Box appears
on the status line and you can add boxes or lines anywhere in the
report layout window.
If you are using a mouse, move the pointer to where you want a
corner of the box to be. Click and drag on a diagonal to create the
box, and release the mouse button when you reach the point where
you want the opposite corner.
If you are using the keyboard, move the cursor to where you want
a corner of the box to be, and press the space bar. Then press the
arrow keys to move the opposite corner into position. Once the box is
the size you want it to be, press Enter.
You create lines in exactly the same way you create boxes, using
either the mouse or the keyboard: just be sure to stretch the box in
only one of the basic directions—up, down, left, or right. (You can¬
not draw diagonal lines—only horizontal or vertical. As soon as you
try to draw a diagonal line, you are necessarily creating a box.)
If you select an existing box (by using the mouse or by putting the
cursor on it and pressing Enter) you will call up the Box dialog box,
shown in Figure 6.8. As you can see from the illustration, the Box
dialog box includes radio buttons that let you choose what character
GENERATING REPOR TS AND MAILING LABELS 225
the box or line is made of. The basic choices are Single Line or Dou¬
ble Line. But you can also select Character to display the dialog box
shown in Figure 6.9 that lets you choose any DOS character. For
example, you might want to create a box made of asterisks to high¬
light some very important data. As you can see from the illustration,
CH. 6
you can even make a box out of smiling faces (if your printer will
print such characters).
If the box you are drawing occurs entirely in the detail band of the
report, the Float As Band Stretches check box appears in this dialog
box. If it is selected, the box will expand vertically if you make the
band larger to display more field data. If it is not selected, the box will
remain the same size when you expand the band, so that the addi¬
tional data will end up outside the box. If you put a box around a
memo field, you should select this check box so that longer memos do
not overflow the size of the box.
Remember that a box or line is an object, and you can move,
resize, or delete it as you do other objects. See the previous sections
on Manipulating Objects Using a Mouse and Using the Keyboard.
FIELD
Selecting Field from the Report menu popup calls up the Report
Expression dialog box shown in Figure 6.10, which lets you place field
expressions in the report layout window as follows: First place the cursor
where you want the field to be located. Then select Field from the
Report menu. Then type the expression to the right of the Expr text but¬
ton (or select the Expr text button to call up the expression builder,
which you can use to create the expression just as you did in earlier
chapters). When you move the cursor after entering the expression (by
pressing Tab or using the mouse), the expression’s width is automati¬
cally entered. Choosing OK places the expression.
You can include a page number in an expression by selecting
_PAGENO from the list of memory variables. This should be used in
the header or footer for long reports.
CH. 6
Table 6.1: Editing Options Check Boxes Available for Formatting Data
Radio Check
Button Boxes
Selected Available Effect
Table 6.1: Editing Options Check Boxes Available for Formatting Data
(continued)
Radio Check
Button Boxes
Selected Available Effect
CH. 6
Character Effect
Text is always
displayed on the
Selecting Type Style Selecting the Style check box calls up the Style
screen in Normal style— dialog box shown in Figure 6.12, which lets you determine the type style
even when you preview in which the fields will be printed. The number of style options you are
the page using Page
given depends on the capabilities of your printer. At most, you are given
Layout from the Record
menu. The attributes you the choice of Normal, Bold, Italic, Underline, Subscript, Superscript,
choose are visible only Condensed, and Double-sized type.
when you print out the
report.
computed fields. As you can see, this dialog box contains six radio
buttons, to select the calculation to be performed on the field:
CH. 6
The default calcula¬ For example, if you had WAGE as the field expression in the Report
tion in the Total Expression dialog box and you checked the Totaling check box, and
dialog box is None. If you
then selected the Average radio button in the Total dialog box, you
do not select the Totaling
check box and use this would create a calculated field that finds the average wage. Notice
dialog box, then no calcu¬ that the Total dialog box includes the Reset popup control, which
lation is performed.
determines how often the calculation will be done. The default is End
of Report, which does the calculation only once, at the end, obvi¬
ously. If you have grouped data, you can also select the name of any
of your groups from the popup, and perform the calculation for each
group; or you can select End of Page from the popup, for example, if
you want to put the total in a footer. The Total field itself must always
be numeric.
Other Features of the Report Expression Dialog Box If you select the
Suppress Repeated Values check box, then if the value of the field is
the same for more than one record, only the first occurrence of the
value will be printed. For example, if you have a report that is
indexed by state, you might want to put the State field at the far left of
the report and select this option so that each state’s name appears
only once.
Finally, you should remember that after a field expression is placed
it is an object, and you can select it and manipulate it as you do any
object. See the previous sections on Manipulating Objects Using a
Mouse and Using the Keyboard.
TEXT
Unlike the case with boxes and field expressions, you do not have
to use the Report menu to position text in the report layout window.
If you wish, you can select Text from the Report menu popup at any
time to enter the Text mode, but the main reason for doing so would
be to edit text that has already been added.
GENERATING REPOR TS AND MAILING LABELS 233
To add text, you can just put the cursor where you want it to begin
and start typing. Until you either press Enter or reach the end of a
line, you can edit the text; after that, the line of text you added is
treated as an object and must be selected and manipulated like a box
or graphic object. The whole block of text is then treated as a single
object.
ft) To edit text after it becomes an object, you can select the object
and then select Text from the Report menu. Alternatively, you can
edit text by moving the mouse pointer to it and pressing Ctrl while
you click the mouse, or by moving the cursor to it and pressing Ctrl
and the space bar.
If you select a text object that is in the detail band by using the
mouse or by placing the cursor in the text and pressing Enter,
the Text dialog box, shown in Figure 6.14, appears.
• Float As Band Stretches: If you check this box, the text will be
printed on the line following the last line of a vertically
stretched field. Fields that use this option must be placed on a
$
• Style: This check box calls up the same Style dialog box
discussed in the previous section on field objects. The Style
CH. 6
dialog box lets you determine the type style in which the text
is printed.
ADD LINE
If you press Shift Selecting Add Line from the Report menu popup lets you make
when you open the bands larger by adding a line to them. The new line is added above
Report menu—by press¬
ing Shift-Alt-R if you are
the current position of the cursor. Select the option as many times as
using the keyboard or by you want for any band; the only limit is that the total number of lines
holding down the Shift in all the bands may not be more than 255.
key while you pop up the
menu using the mouse—
the popup wiD include an REMOVE LINE
Add Line After option
instead of the ordinary Selecting Remove Line from the Report menu lets you make
Add Line option. This bands smaller by deleting the line that the cursor is in. If you have
option inserts the line
after the current position
already entered anything on this line when you select this option,
of the cursor. FoxPro will ask if you want to delete the objects on the line. If you
choose Yes, it will delete both the line and the objects on it.
CENTER
Select an object and then select Center from the Report menu in
order to center the object on its line. Note that the location of the
‘ Tenter” of the line depends on the margins that you choose by
selecting Page Layout. Furthermore, if you are centering a field
object, you must choose the Center check box from the Format dia¬
log in addition to choosing this option.
QUICK REPORT
Selecting Quick Report from the Report menu calls up the Quick
Report dialog box shown in Figure 6.15. You can use this dialog box
GENERATING REPORTS AND MAILING LABELS 235
• Column Layout: places the fields in the detail band one next
to another, from left to right.
• Form Layout: places the fields in the detail band one above
another, from top to bottom. The detail band will automati¬
cally stretch to hold all the fields.
• Field: displays the field picker dialog box (which you looked
at in the last chapter) to let you choose which fields are ini¬
tially displayed in the quick report.
Since it only includes fields and not field expressions, the Quick
Report option is of limited use.
236 MASTERING FOXPRO
CH. 6
A SAMPLE REPORT
With this background, you should have no trouble creating a sophis¬
ticated sample report. In this exercise, you will create a report that
groups employees by state, listing their names (alphabetically) and their
wages. Among other features, the report will include group footers with
the number of employees and the average wage for each state and a
report footer with the same information for all the employees.
2. The EMPLIST file is now open with this new index active,
so you are ready to design the report. Select File New from
the File menu popup, select the Report radio button, and
then select OK to call up the report layout window.
3. Set the report margins using Page Layout from the Report
menu. Make the top margin 6 rows, the bottom margin 6
rows, the printer indent 10 columns, and the right margin
column 65. Then select OK.
5. Add a few extra lines to the title band: The cursor should
already be in the title band. Select Add Line from the Report
menu to add an extra line. Repeat this step two more times,
so the title band has four lines in all.
GENERATING REPOR TS AND MAILING LABELS 23 7
6. Add the title: Press the down arrow to move the cursor to the
second line of the title band, and type
7. Put a box around the tide: Move the cursor to row 0, column 19
(one row up from and two columns to the left of where the tide
begins). Then select Box from the Report menu. Use the key¬
board or the mouse to draw the box so it is centered around the
tide, as shown in Figure 6.16.
8. Create the page header: First remove one line from the PgHead
band. Move the cursor to that band and select Remove Line
from the Report menu. Move the cursor to the top line of the
page header band and to the left edge of the screen. Select Field
from the Report menu. To the right of the Expr text button,
type
CH. 6
Press Tab and note that the width of the expression you
entered, 30, automatically appears. Select OK. Note also
that the expression as it now appears on the report seems
incomplete. This is because it can take up only 30 spaces, the
actual width the expression’s result will occupy on the report.
9. Add group bands: Select Data Grouping from the Report
menu. When the Group dialog box appears, select Add. Then,
when the Group Info dialog box appears, type STATE to the
right of Group, and select OK. This returns you to the Group
dialog box where STATE is added as group 1. Select OK.
Notice that the group header and footer named 1-STATE have
been added to the report layout window.
10. Add the group header: Move the cursor to that band. Select
Add Line twice from the Report menu so that there are three
lines in the band. Move the cursor to its second line, at the
left edge of the screen. Select Field from the Report menu. In
the Report Expression dialog box, to the right of the Expr
text button, type (in all capital letters)
11. Enter the detail line: Move to the detail band. Select Remove
Line twice from the Report menu to make it just two lines.
Move the cursor to the second line of the band, flush with the
left margin. Select Field from the Report menu. Since the
WAGE of the detail line is not used in a calculation, you can
enter the entire detail line as a single string expression. In the
Report Expression dialog box, to the right of the Expr text but¬
ton, type
dollar sign before it, using LTRIM to make sure that there is
no space between the number and the dollar sign. Press Tab,
and the width—42—is automatically entered. Select OK.
12. Add the group footer, which will summarize how many
workers there are in the given state and their average wage:
Move the cursor to the group footer line. Select Add Line
three times from the Report menu so that there are four lines
in the band. Move the cursor to the second line in the band,
at the left margin. Select Field from the Report menu to call
up the Report Expression dialog box. You can count any
field to get the number of workers; we’ll use LNAME. Enter
this to the right of the Expr text button. Then select the
Totaling check box to call up the Total dialog box. Select
the Reset popup control and select STATE from the popup
that appears; then select the Count radio button; and select
OK to return to the Report Expression dialog box. Since a
computed field must be numeric, select Format, then select
the Numeric radio button and select OK. Since you know
that there will be no more than 99 employees in any of the
states, enter 2 as the width of the computed field. Then select
OK. Only the first two letters of the field name, in this case
LN, are displayed to show where the number goes.
14. Press the right arrow key twice to leave a space before the
amount of the wage. You want to left-justify this amount so
that there are no extra spaces between it and the preceding text
if the number is small. Select Field from the Report menu. In
the Report Expression dialog box, type WAGE to the right
of the Expr text button. Select the Totaling check box. In the
Total dialog box, select the Reset popup control and select
240 MASTERING FOXPRO
CH. 6
15. Add a page footer: Move the band to the last line of the footer
band. Type
18. Select Page Preview from the Report menu to preview the
report. The first screen displayed should look like Fig¬
ure 6.18. Select More if you want to page through the report.
Select Done when you have seen enough.
GENERATING REPOR TS AND MAILING LABELS 241
PgHead
PgHead
r1—STATI
r1-STATE|"EMPL0YEES IN THE STATE OF "
rl-STATf
Detai1
Detail _|PROPER(LNAME+" "+FNAME)+" $"+LTRIM(STR(WA6E
L1—STAT
Ll-STATE|LN "EMPLOYEES FROM " + STATE + WAGE
Li—STAT
Li-STAT
PgFoot.
PgPoot
PgFoot
PgFoOt Report on wages by state
Summar
Summar
Summar
SummaryflLN EMPLOYEES IN TOTAL: AVERAGE WAGE WAGE
Figure 6.18: Using the Page Preview feature to test the report.
19. Select Save As from the File menu to use the Save Report As
dialog box, shown in Figure 6.19. Note that the Save Envi¬
ronment check box is already checked: this is the default.
Type the name ST_WAGE (for the State Wage report), as in
J
CH. 6
the illustration, and select Save. Now that you are finished
designing the report, close the report layout window as you
would any window.
20. Now select Report from the Database menu. Note that in the
Report dialog box, shown in Figure 6.20, the Environment
check box is already checked by default, which means that
the index will be opened automatically. Select the Form text
button at the upper left to call up the Report file dialog box,
and select STJWAGE.FRX.
21. In the Report dialog box, neither To Print nor To File have
been checked, but the Console On radio button is selected.
This means that when you produce the report, it will be dis¬
played on the screen but will not go to the printer or to a text
file. (You can change these settings if you want.) Select OK
to produce the report. Be patient: it can take a while before it
scrolls by. If you are just producing it on the screen, all the
information is displayed just as it would be on a page.
You might want to modify this report and try other features of the
report generator on your own. For example, you could try different
type styles or try making each group start on a new page, or try using
GENERATING REPOR TS AND MAILING LABELS 243
Report:
Shiie!..
lain
_ Eject
Summarjjj
Heading
To flrint
' Do File
,• fflonsole On ( ) Console
CH. 6
e
H T Spaces
i 5 i—t —►
9 Between
h
■(- T
t
1 Lines Between
i
After you have designed and saved the label form you want, you
can print the labels at any time by selecting Label from the Database
menu to call up the Label dialog box, shown in Figure 6.22.
This dialog box is very similar to the dialog box you use when you
select Report from the Database menu to print a report. As you can
guess, the Form text button lets you choose which of the existing label
forms to print, and the Environment check box next to it lets you use
the environment setting that you saved when you created the labels.
The Scope, For, and While check boxes let you print labels for
records that meet certain criteria. The To Print and To File check
boxes let you send the labels to the printer or to an ASCII file, and the
Console On and Console Off radio buttons determine whether
the labels are displayed on the screen, just as with reports.
The one difference is the Sample check box. This feature lets you
print a single sample label in order to check the alignment of the label
paper in your printer. The sample label will contain asterisks to show
you where data goes on the label. After the sample is printed, a dialog
box appears asking if you want another sample. If the printer is out of
alignment, you can move the label paper and then select Yes from
this dialog box to see if the new alignment is correct. If the paper is
correct, select Do Labels to print all the labels.
246 MASTERING FOXPRO
CH. 6
• 3 V2" X 15/l6" X 1
• 3 V2" X 15/l6" X 2
• 3 V2" X 15/i6" X 3
• 4" X 1 7/l6" X 1
As you can see, not all of these layouts are restricted to labels. If
your printer is capable of it, they also let you print directly on the two
standard sizes of envelope, on 3-by-5-inch index cards (or that size
Rolodex cards), and on the other standard size of Rolodex cards.
If none of these standard layouts is adequate, you can start with the
one that is closest to what you need and customize it by simply chang¬
ing the settings in the layout window. For example, you can see that
the left margin back in Figure 6.21 is 0; if you want to add a
1-inch left margin, just change that number to 10 (assuming that you
are using a standard printer with ten characters per inch). Likewise,
you can edit the width, height, lines between, spaces between, and
GENERATING REPOR TS AND MAILING LABELS 24 7
number across to create any label layout you choose, and edit the
remarks to change the size description.
Notice this other When you have the right layout size, just enter expressions in the
difference from the
report layout window.
sample label on the window. You can use the expression builder to do
When you are designing this by selecting Expression from the Label menu popup, or you can
reports, you must use the just type in the expressions.
menu to add expressions,
Remember that any text enclosed in quotation marks (or in the
since anything you just
type is treated as text. On other delimiters that FoxPro allows for character literals) is a valid
the other hand, there are FoxPro expression. If, for example, you run a membership organiza¬
only expressions on label
tion and you are using a FOR clause to print labels for people who
forms. Thus, you can just
type expressions in as have not paid their dues, you can include the expression “PLEASE
well as using die menu to PAY YOUR DUES” somewhere on the label.
add them. Often, a line of a label must include the contents of two fields with
just a blank space between—for example, the first name field and the
last name field. You can use the expression
to print this, but since it is so common, FoxPro also gives you a short¬
cut. If you simply separate each field expression with a comma, Fox¬
Pro trims the contents and puts one space between.
If there is a possibility that an expression will evaluate to a blank
space, you should add a semicolon after it so there will not be a
blank line left in the labels. You will do this for the apartment num¬
ber when you are creating sample labels, since that field is blank in
many records.
That’s about all there is to creating label forms. The Label menu
popup, shown in Figure 6.23, is very easy to understand. It has just
five features.
• Page Preview: lets you see on the screen how the labels will
appear in print. It works just like the feature with the same
name on the Report menu.
CH. 6
Now, you should have no trouble laying out some sample labels:
2. To start designing the labels, select New from the File menu
popup, select the Label radio button in the New dialog box,
and select OK.
GENERATING REPORTS AND MAILING LABELS 249
3. The label layout window appears, with the cursor on the first
line of the label form. Type
PROPER(FNAME),PROPER(LNAME)
and press Enter. On the second line, type
PROPER(ADDRESS)
and press Enter. The third line contains the apartment num¬
ber with ten spaces before it, so it is indented, and a semi¬
colon after it, so there is no blank line for addresses without
an apartment number: type
H PROPERt FNAME).PROPER(LNAME)
e PROPER(ADDRESS) Spaces
i 5 " "+APT NO; i—0 —►
g proper(trim(city7)+", "+UPPER(STATE Between
t
t
1 Lines Between
i
CH. 6
You should also try some other layouts. Select Layout from
the Label menu, select other default layouts, and select Page
Preview to see how they look.
7. Save this custom layout. Select Save Layout from the Label
menu. When the Save As dialog box appears, select OK to save
it under the suggested name. Select Layout again from the
Label menu to confirm that your custom layout has been added
at the end of the list of layouts, as shown in Figure 6.26.
Save the label form. Select Save As from the File menu. Note
that the Environment check box is checked by default. Enter
the name TWO_COL, since this form prints two column labels,
and select Save. Then close the label layout window as you
would any window.
GENERATING REPORTS AND MAILING LABELS 251
Figure 6.26: The label menu popup with the custom form added.
9. Select Label from the Database menu. The Label dialog box
is the same as the dialog box you used to produce reports.
Select Form, and then, from the Label File dialog box, select
TWO_COL.LBX. Select OK from the label dialog box to
send the labels to the screen.
WHAT NEXT? -
Now you have learned all the basic features of FoxPro that are
needed for most ordinary purposes. You can define the structure of a
database; add, edit and view data; create indexes; query to find data
you want; and create reports and mailing labels. This is all you need
to know for most basic database applications.
At this point, you must choose how to continue your work with
FoxPro.
If you have an application that you can manage with the tech¬
niques that you have learned so far—such as running a mailing list—
you might want to go ahead and get practical experience with that
application without learning any more about FoxPro. Before you do
this, though, you should look at the brief discussion of relational data¬
bases in the next chapter to see if you might need these techniques to
manage your data.
252 MASTERING FOXPRO
CH. 6
If you want to go right ahead with this book, you can either go
ahead to Part II or skip right to Part III, depending on your interests.
Part II covers more advanced FoxPro techniques. It takes you
through the menu options that have not been covered yet and teaches
you to create keyboard macros, to create formatted input screens,
and to use the applications generator to create entire menu-driven
applications that can be used by people with absolutely no experience
with FoxPro. If you want to explore every facet of FoxPro and to
become a power user, go on to Part II.
Part III includes an introduction to computer programming with
FoxPro and then teaches you to create a menu-driven mailing list
application, a program that is as powerful as many commercial appli¬
cations. If you are eager to learn about programming, you can skip
Part II for now and go right to Part III. You should go back to Part II
later, however, when you want to learn advanced techniques to add
more power to your programming.
ART II
Using the View Window
with Relational Databases
To create a View, 263
select View from the Window menu to call up the View win¬
dow. Use the panels of this window to set environment vari¬
ables. Select Save As from the File menu to save these settings
in a .VUE hie.
CH. 7
UNDERSTANDING
RELATIONAL DATABASES _
CH. 7
A view can be set up that lets the payroll department scroll through the
records and look at the name, address, date, and wage just as if they
were in a single database file. This is an example of a one-to-many relation¬
ship: each employee has one name and address, but many weeks of
wages.
Though it is mean¬ Notice that the key field must be unique: it cannot be duplicated in
ingful, the Social
Security number is
more than one record in the file on the “one” side of the relation. If
acceptable as a key field, two employees had the same employee number, for example, there
since it is unique for each would be no way of knowing which one of them corresponded to a
person and never
wage record with that employee number. The key field must also be
changes.
unchanging: if you ever change its value in a record on the “one”
side of the relation, than you will have no way of relating the records
on the “many” side to it. For these reasons, you should use some
arbitrary value, such as an employee number, as the key field, and
you should never use some meaningful value, such as the person’s
name. A meaningful value might be duplicated; and it might change.
For example, two people may have the same name; furthermore,
people sometimes change their names.
Needless to say, the job of normalizing the data, breaking it down
to avoid repetition, .can be very complex if you are computerizing a
large corporation. There is an entire theory of database normaliza¬
tion that you should study if you become interested in advanced data¬
base programming. For most applications on microcomputers,
though, normalization is just a matter of common sense: you simply
have to look for one-to-many relationships.
In the example you looked at above, one employee gets many pay-
checks. In some applications, there are also many-to-many relationships.
One common example is enrollments of students in classes: each stu¬
dent can take many classes, and each class can have many students
enrolled in it. This sort of relationship will not really be covered in
this book, because many-to-many relationships are not common in
applications on microcomputers. It is good for you to know that they
exist, however, just in case you run across one—so that you will not
try to handle it as a one-to-many relationship. The theory of data¬
bases with many-to-many relationships is covered in more advanced
books. Since they are broken down into pairs of one-to-many rela¬
tionships, they can be handled using techniques similar to the ones
you will learn for one-to-many relationships.
USING THE VIEW WINDOW WITH RELATIONAL DATABASES 263
CH. 7
them in one of the following ways, all of which use the arrow operator
that you have seen before in commands generated by FoxPro:
• the file name (or alias), followed by the arrow operator - >
Programmers some¬
times open files with and the field name
an alias, to make it easier
to follow the code. You can The arrow operator is made up of two characters, a hyphen followed
do this by using the com¬
by a greater-than sign.
mand USE <.file name>
ALIAS KaliasnameA, You can also move among work areas by using the command
after which you can refer SELECT with any of the preceding methods to refer to the work area.
to the file by its alias rather
For example, if you have the EMPLIST file open in Work Area A,
than its name.
you can move to that work area and use that file in the ordinary way
by entering SELECT A or SELECT 1 or SELECT EMPLIST. Notice
that the arrow operator is not used to move among work areas. In
these situations, it is used only to refer to fields that are not in the cur¬
rent work area.
USING THE VIEW WINDOW WITH RELATIONAL DATABASES 265
CH. 7
3. Now, since the View window includes the entire Setup dialog
box, you can use it to modify the structure of the EMPLIST
database to add an employee number. Select View from the
USING THE VIE W WINDOW WITH RELATIONAL DATABASES 267
Structure: Untitled
Name Type Width Dec
Field
± EMPNO Character 3
X DATE Date 8 < Insert>
X WAGE Numeric 7 2
<Delete>
« OK »
<Cancel>
Empno A01
Date 08/13/90
Wage 740.00
Empno A02
Date 08/06/90
Wage 530.00
Empno Hjj
Date H
Wage
▼ Command
CREATE Untitled
CH. 7
USE C:\LEARNFOX\EMPLIST.DBF
Remember that 4. To modify the structure of EMPLIST, select the Setup text
there are two Modi¬ button from the View window. From the Setup dialog box,
fy text buttons in the
select the Modify text button. When the Structure dialog box
Setup dialog box. You
need to use the one next appears, move the highlight to the FNAME field; then select
to the word Structure, not the Insert text button or select Insert Field from the Structure
the one under the word
menu to add a new field. Change the name of the field that is
Index.
added from NEWFIELD to EMPNO, keep its type as Charac¬
ter, and change its width from 10 to 3. The structure should
look like Figure 7.4. Then Select OK and, to make the structure
change permanent, select Yes. When you return to the Setup
dialog box, the new field is added at the beginning of the scrolla¬
ble list of field names. Select OK.
L
USE C:\LEARNF0X\EMPL
1 a t Command
SELECT B
USE C:\LEARNFOX\EMPLIST.
BROWSE LAST
6. To index this file, select the Setup text button. Select the Add
text button in the Index box. When the Open Index File dialog
box appears, select the New text button. When the Index On
dialog box appears, select EMPNO from the scrollable list of
field names and then select OK. When the Index File Name
dialog box appears, type the name EMPNOS and select OK.
When you return to the Setup dialog box, notice that the new
EMPNOS index is active as the main index that sets the order
of the records—exacdy what you need. Select OK.
270 MASTERING FOXPRO
CH. 7
7. Now you are ready to set the relation. Remember that you
must be in the work area of the file on the “many” side of the
relationship and set the relation into the file on the “one’ ’ side of
the relationship, since FoxPro needs to look into the EMPLIST
file to find one record that matches each record in the WAGES
file. Move the View window’s highlight to WAGES and press
Enter to generate the command SELECT A. If FoxPro also
opens a Browse window and generates the command BROWSE
LAST, close the Browse window to return to the View window.
Then select the Relations text button. Notice that WAGES, the
name of the current file, appears in the Relations window, with
an arrow pointing to the space under it for the file that the rela¬
tion is set into.
8. Move the highlight to EMPLIST and press Enter to select it as
the file that the relation is set into. The expression builder
appears to let you choose the expression in WAGES that corres¬
ponds to the indexed expression in EMPLIST. Notice that you
can use any expression from the file on the “many” side of the
relationship, but that you must relate it to the indexed expres¬
sion in the file on the “one” side of the relationship. Type
EMPNO in the text box and then select OK. Now that the rela¬
tion is set, EMPLIST appears under WAGES, with the arrow
pointing into it, as in Figure 7.6. The command SET RELA¬
TION TO EMPNO INTO EMPLIST is generated.
Now that the relation is set, you can browse both files and see that
when you move the pointer in the WAGES file, FoxPro automati¬
cally moves the pointer to the corresponding record in the EMPLIST
file. This exercise will help you understand how the relation affects
the pointers in the two files. (In a later exercise, you will set up the
relational database in more practical ways, for example by including
fields from the two files in the same Browse window.)
-D-
< Misc > -E-
-F-
<Setup > -G-
-H-
<Browse> -I-
<
\ On p n
kj yj ^ i i >/
Figure 7.6: The relation of WAGES set into EMPLIST, shown in the View
window.
CH. 7
WAGES Browse window. The pointer is still where you left it,
on the fourth record, which has the Empno of A02. Select 1
EMPLIST from the Window menu to return to the EMPLIST
Browse window. The pointer is not where you left it: it moves
back to the second record, so that its Empno corresponds with
the current Empno in the WAGES file. Now close both Browse
windows to return to the View window.
Of course, it would take too much time to set the relation each time
you wanted to use this relational database. In the next section, you
will save and reuse the view, after you see how to make use of the
related files.
set up is saved and reused automatically each time you select Browse
from the Database menu, generating the command BROWSE
LAST. If you use BROWSE FIELDS <Lfield list> once to create the
Browse window, the Browse window will be displayed in the same
way whenever you select Browse from the Database menu.
The key field from As an exercise, try creating a Browse window that includes all the
the file on the
“one” side of any one-to-
fields of the WAGES file, and the Empno and name fields of
many relation must be the EMPLIST file, to see how easy this makes data entry. Having the
protected from being Empno fields from both files will let you see clearly that the fields added
changed accidentally,
to the Browse window from the EMPLIST file correspond to the cur¬
otherwise it can cause
irrecoverable loss of data. rent record in the WAGES file. It will also show you an important pitfall
The Empno field from that you must avoid when you are working with relational databases.
the EMPLIST file is
Before you begin, make sure that you closed both Browse windows
included in the Browse
window in this exercise at the end of the last exercise, and that the work area of the WAGE
only for instructional file is the current work area.
purposes.
CH. 7
Figure 7.8: Fields that correspond to the Empno you enter are automatically
filled in.
USING THE VIEW WINDOW WITH RELATIONAL DATABASES 275
. ■
!
j
▼ Command
_|LAST
SELECT B
BROWSE LAST
BROWSE FIELDS EMPNO, DAT
5. To fix this mistake, select View from the Window menu. In the
View window, move the cursor to the work area with
EMPLIST in it and press Enter, to generate the command
SELECT B. If FoxPro does not automatically open a Browse
window, select the Browse text button. In the new Browse win¬
dow, you can see that two records have the empno of A04.
276 MASTERING FOXPRO
CH. 7
Hopefully, you remember that Edna Chang is the one that used
to be AOS, since it is no longer in its proper order. Edit the file so
Edna Chang again has number A03 and close this EMPLIST
Browse window, saving the change. Close the View window to
see your WAGES Browse window again. The empno, lname,
and fname reappear in the records where they were missing.
6. Now that you have seen what can go wrong, you will save
this view and then reuse it as an exercise. First, save the view:
Select View from the Window menu to open the View win¬
dow again. Then select Save As from the File menu, and
FoxPro displays the Save View As dialog box, shown in Fig¬
ure 7.10. Type the name WAGEENTR and select Save, gen¬
erating the command
7. Now, watch how easy it is to use this view at any time in the
future, even after you have quit FoxPro. Select Quit from
the File menu to end this session; then, at the DOS prompt,
enter FOXPRO to start FoxPro again. (If you want, enter
CLEAR to clear the screen, or start the program using
FOXPRO -T).
USING THE VIEW WINDOW WITH RELATIONAL DATABASES 277
8. Select Open from the File menu. From the Open dialog box,
select the Type popup control. Select View as the type, as in
Figure 7.11. Notice that FoxPro gives you the choices of the
environments that you saved when you created reports and
labels as well as the .VUE file you just created, as illustrated
in Figure 7.12. Select WAGEENTR.VUE from the scroll¬
able list and note that FoxPro generates the command SET
VIEW TO WAGEENTR.VUE. Now, select Browse from the
Database menu, and the Browse window that you set up to
display fields from the two files reappears. Close the Browse
window.
Open :
► [..] Drive C
TESTCOPY.DBF
WAGES.DBF
Directory LEARNFOX
« Open »
5 < New
Database
Program I Type < Cancel
L
File
Index
Report
-T-
CH. 7
Figure 7.12: The list of View files includes environments for reports and
labels.
you used a fields list when you were working from the Command
window. Unfortunately, the Set Fields check box of the Setup win¬
dow cannot be used in this way; it can only exclude fields from the
current file and cannot include fields from related files. Later versions
of FoxPro are expected to let you use this check box to select fields
from multiple files of relational databases. Then you could just SET
FIELDS once and not have to worry about it again. In the meantime,
try using the Fields check box of the Copy To dialog box:
Database:
WAGES
EMPL1ST I <@ancel
«
>
Figure 7.13: Using the Database popup control to work with related database
files.
Database:
-—-- <@ancel >
WAGES
« g)K »
L i
Figure 7.14: The field picker with fields from two related database files.
2. You have returned to the Copy To dialog box, and you are
ready to copy the selected fields to a new file. In the Save As
text box, type TESTCOPY, and then select OK.
280 MASTERING FOXPRO
CH. 7
3. To see the result, select View from the Window menu to re¬
open the View window. Move the highlight to Work Area C
and press Enter to generate the command SELECT C. If the
Select Database dialog box does not appear automatically,
select the Open text button of the View window. Select
TESTCOPY.DBF from the scrollable list of file names and
then select the Open text button. If necessary, select the
Browse text button of the View window to browse this file to
see the TESTCOPY file. You will find that it has the fields
from both the EMPLIST and WAGES files, as shown in
Figure 7.15.
System File Edit Database Record Program Window Drowse ;V. '• . '
1 TESTCOPY
I name Fname Date Wage
I
lAudrey 1 720.00
Levy Audrey 08/13/90 740.00
LOVE JACK 08/06/90 530.00
LOVE JACK 08/13/90 590.00
CHANG EDNA 08/06/90 498.00
CHANG EDNA 08/13/90 480.00
S3 TESTCOPY FIELDS
SELECT C
USE C:\LEARNFOX\TESTCOPY
BROWSE LAST
Figure 7.15: Fields from related files copied into a single file.
controlling file, the file which is on the “many” side of the rela¬
tionship. This file must be in the current work area when you
use the report, as when you use any command with a rela¬
tional database.
2. Select New from the File menu. Select the Report text button
and then select OK to call up the report layout window. Press
the down arrow key four times to move the cursor to the
detail band.
CH. 7
WARNING
\
The most important thing you should have learned from all these
exercises is how much damage you can do by modifying the indexed
key field of the database that the relation is set into. If you do this by
mistake, you could end up with a list of wages and employee num¬
bers without having any way of finding out which employee has a
given employee number. Or you could end up with lists of customer
numbers, sale dates, and amounts of money owed to you without
having any way of finding out the names, addresses, or phone num¬
bers of the customers you have to bill.
Never include a key field of this sort in the Browse window in the
way that we did in the exercise. That example was meant to teach you
graphically about a danger you need to avoid. Do not even include this
sort of key field in the Browse window that you use to update the file
itself; instead, use a Browse window with all the other fields. This way,
you can change the name and address but you cannot change the
employee number or customer number even by mistake. Moreover,
do not delete records in this file unless you are archiving all of your old
data and beginning a new cycle of data entry. If you do delete a record
in this file, you will not be able to use the corresponding records in the
USING THE VIEW WINDOW WITH RELATIONAL DATABASES 283
related file. Finally, always keep your database files backed up, in case
the mistake does occur despite your precautions.
In fact, because of this danger, the best way to use a relational
database is by writing a program that adds the key field automatically
and never lets the user change them. It is better yet if the user never
even sees them.
CH. 7
Figure 7.17: The On/Off panel of the View window with default settings.
CH: 7
• Help: lets you specify which file is to be used when the user
selects Help from the System menu (or presses FI). You can
create your own help files if you are creating an application
where the user does not need and would only be confused by
all the information in FOXHELP.DBF, the help file that
comes with FoxPro—which, as you can see, is the default
help file. This feature is equivalent to the command
• Set Resource To: lets you specify the resource file that FoxPro
uses. The resource file stores information about the location
and size of your Browse windows, color selections, and other
preferences. By default, FoxPro automatically creates a
resource file named FOXUSER.DBF if, for example, you
change your Browse window; then it uses this file to set up
the Browse window when you use the command BROWSE
LAST in a later session. You can create a variety of resource
files with different names and use them for different pur¬
poses. You can also set Resource on or off using the On/Off
panel; the default, of course, is on.
CH. 7
the date format are controlled by the check boxes to the right
of this popup.
• Century: lets you display the entire four-digit year, not just
the last two digits. The equivalent command is SET CEN¬
TURY ON or OFF.
• Clock: lets you use and adjust the system clock. When the
check box is checked, the system time is displayed on
the screen. The command equivalent is SET CLOCK ON.
The popup lets you display the time in 12- or 24-hour format.
USING THE VIE W WINDOW WITH RELATIONAL DATABASES 289
CH. 7
Remember that all the environment settings from all these panels
are saved when you save the view in a .VUE file. They will all be in
effect again whenever you open that .VUE file.
Getting the Most
from the Menu System
To create a keyboard macro, 297
press Shift-F 10 at any time. Then enter the keystroke combina¬
tion that you want to use to activate the macro. Press Shift-FlO
again to stop recording the macro.
CH. 8
KEYBOARD MACROS _
Many programs let you create keyboard macros. A macro simply
records a series of keystrokes and assigns them to some special key or
key combination, so that you can press one key or key combination
each time you need to use the series of keystrokes you have recorded.
Macros are a convenience to save you time in entering keystrokes
that you use frequently. Though you can save any sequence of key¬
strokes in a macro, generally you will use them to save data-entry
time. For example, if you have to enter a large number of records
with addresses in San Francisco, you can create a macro that stores
the keystrokes needed to type SAN FRANCISCO, to move to the
State field, and to type CA. Macros are also useful for customizing
the editor, for example, to make it work like an editor that you are
more familiar with.
FoxPro lets you assign a macro to any of the function keys—the keys
on the left or top of your keyboard, labeled with F and a number—and
to a large number of key combinations that use Ctrl, Alt, or Shift with
function keys or letter keys: remember that only letter keys and func¬
tion keys can be used in macros, not numbers, special characters, or
CH. 8
Default macros The function keys by themselves are assigned default macro values
that you create are
saved in a file named
if you have never created macros for them. FI is help, and because
DEFAULT.FKY in this is very useful, it cannot be assigned another value. The other
either your FoxPro home function keys’ default values are left over from the days when dBASE
directory or in the cur¬
did not have a menu interface; they let you enter the most common
rent directory. Until you
create new defaults, this commands at the command line. These default macros are no longer
file does not exist, and useful now that it is easier to use the menus. As you will see, you can
FoxPro simply generates
save new default values for these function keys so that they will be set
the standard defaults
when the program is automatically whenever you start FoxPro.
started. If default macros Selecting Macros from the System menu calls up the Keyboard
that you have saved are Macros dialog box, shown in Figure 8.1. When this dialog box is dis¬
not available when you
start FoxPro, search for
played, a Macros menu pad is added to the menu bar; the Macros
the DEFAULT.FKY file. popup is shown in Figure 8.2. As you can see, the menu popup sim¬
ply duplicates the choices that you can make by using the text buttons
of the dialog box—the menu is added so that you can use the Control-
key combinations as an alternate way of making these choices, if you
find it more convenient.
Keyboard Macros
<Set Default>
Macros
jlear
Clear 011
Save Macros
Restore Macros acros
Set jjefault
CH. 8
Macro Name:
• Continue: Return to the point where you were when you left
off and continue to create and record the macro.
Insert Pause is the most interesting of these. It lets the user interrupt
the macro in order to type text of any length; then, when the user presses
Shift-FlO, the macro continues. For example, you can create a macro
302 MASTERING FOXPRO
CH. 8
that enters your return address at the top of a letter, pauses, and then
enters the salutation. To use the macro, you let it enter the return
address, then you take advantage of the pause to enter the address of the
person you are writing to, and then you press Shift-FlO to let the macro
continue, which it does by skipping a line, typing the word Dear, and
leaving the cursor where you need it to type the rest of the name.
The Insert Pause text button has two radio buttons associated with
it, which let you control how the pause is ended:
In general, Key To Resume is the better choice, since it lets you take
as much time as you need to make the entry. Seconds is useful pri¬
marily if you want the macro to continue executing after a pause even
if no value is entered.
GETTING THE MOST FROM THE MENU SYSTEM 303
Once the macro has been recorded, use it by pressing the key com¬
bination that you entered in the Macro Key Definition dialog box.
If a macro does not work properly, the problem probably results
from your being in the wrong place when you used it. To give an
obvious example, if you saved the keystrokes needed to type San
Francisco, you must be in the City field of your database when you
use the macro.
WORKING WITH
CURRENT AND SA VED MACROS
Once you have created a macro using the methods outlined above,
it is a current macro, which appears in the scrollable list in the Keyboard
Macros dialog box. Current macros exist only temporarily, unless
they are saved.
Macros that you have saved in past sessions are kept in a disk file
with the extension .FKY. They do not appear in the scrollable list in
the Keyboard Macros dialog box, and thus are not usable until you
restore them and add them to the list of active macros.
Dividing macros into sets lets you group macros for different appli¬
cations. For example, there might be one group that you use when
you are editing programs, and others that you use when are you
304 MASTERING FOXPRO
CH. 8
doing data entry in different files. All of the macros that are being
used at a given time appear in the scrollable list, and you can save
them all as a set with a single name. Then you can recall and use that
set whenever you need it.
To save the current set of macros, select Save from the Keyboard
Macros dialog box or choose Save Macros from the Macros menu
popup. The familiar Save As dialog box appears, with all of the sets
of macros in the current directory in its scrollable list. Select one of
these names to overwrite an existing macro set, or enter a new name
to create a new macro set.
To use a set of macros that has been saved, select Restore from the
Keyboard Macros dialog box. The familiar Open dialog box
appears, with the heading Restore Macros From File above a scroll¬
able list of macro set names. Select any one and select Open to use
those macros.
Remember that the macros you restore are added to the macros
that are already open, which are in the scrollable list of the dialog
box. At some point you might want to get rid of some or all of the cur¬
rent macros before adding new ones. To get rid of a macro, select it
from the scrollable list, and then select the Clear text button or select
Clear from the Macros menu. To get rid of all the current macros,
select the Clear All text button or select Clear All from the Macros
menu. These options only clear the macros from current memory—
they do not erase the file where they are saved on disk.
Finally, to make the current set of macros the default set, the set that
is automatically used whenever you start FoxPro, just select the Set
Default text button or select Set Default from the Macros menu
popup. FoxPro asks you to confirm this selection, then it stores the
current macros in a file named DEFAULT.FKY, which it automati¬
cally uses to set the default whenever it is started. You can begin by
saving one or two macros that you always find useful as the default,
and add more default macros as you invent more.
All the features of the File menu that you have not yet learned are
connected with creating and printing text files. When you use these
features, you are moving in the direction of using the FoxPro editor
GETTING THE MOST FROM THE MENU SYSTEM 305
New:
(' ) Batabase
( ) arogram
( ) Jile |« OK
( ) Index
( ) Report < Cancel >
( ) Label
( ) Form
CH. 8
control characters of their own; both have just the standard ASCII
characters.
The difference between them is in the default editor settings that
they use. The major difference is that the default editor setting for
text files includes the word-wrap feature, which automatically moves
the cursor to the next line when you get to the right margin. Since
program files must keep each command on a line of its own, the pro¬
gram editor sets word-wrap off by default.
SETTING UP
THE PRINTER AND PRINTING A FILE
Select Printer Setup from the File menu to display the Printer
Setup dialog box, shown in Figure 8.7.
Printer Setup:
Print to:
<File... >
The popup control here lets you choose the device to print to. The
default is PRN, which represents your printer. You can also use this
control to print to a file. To do this, you must specify the name of the
file that the output goes to, either by selecting the File text button and
entering the file name in the Print To dialog box or simply by typing
the file name next to the File text button. The Print On and Print Off
GETTING THE MOST FROM THE MENU SYSTEM 307
Use the Windows popup control of this dialog box to choose the
source of the text that will be printed. You can choose to print any of
the following:
• the text in the clipboard (that is, text that you have used the
Edit menu to copy)
• the text in any open editing window (that is, the text of a pro¬
gram or text file)
• the text in any file that is not open
308 MASTERING FOXPRO
CH. 8
You can select the first three of these from the Window popup con¬
trol. For the fourth, printing the text in a file that is not open, select
the File text button to choose the file you want from a scrollable list
in the Print File dialog box, or just enter the name of the file you want
to print next to the File text button.
If you select the Line Numbers check box, FoxPro numbers
the lines of the file that it prints. This feature is meant primarily for
programmers.
• Clear: deletes (or clears) text that is marked. Since you can
also delete marked text simply by pressing Del or Backspace,
there is little need to use Clear.
• Select All: marks (or selects) all the text in the document. This
is sometimes a handy shortcut.
After these two simple features, there is a group of very useful fea¬
tures that let you move around the document, search for specific
words, and even do search-and-replace. There is also a feature that
lets you change the default settings of the editor. With the addition of
these features, the FoxPro editor is as powerful as many commercial
word processors. They are covered in detail here.
GOTO LINE
Selecting Goto Line from the Edit menu calls up the Goto dialog
box, shown in Figure 8.9, which lets you move the cursor to any line
in the document, if you know its line number. (Of course, if the word¬
wrap feature is on, the line numbers will change whenever the
text is rejustified.) Just enter the number of the line you want to move
to and then select Goto to execute the command.
GETTING THE MOST FROM THE MENU SYSTEM 309
Line Number:
FIND
Find can also be Selecting Find from the Edit menu calls up the Find dialog box,
used to search for
shown in Figure 8.10. The items in this dialog box let you search
text in the Browse
window—for example, as
for text—a word, several words, or just a few letters—in the current
a quick way to search for document.
a person’s name. Note Just type the text you are searching for in the Look For text box.
that when you are in the
You can search for control characters by using \r to stand for carriage
Browse window, the Find
dialog box does not return, \t to stand for tab, \n to search for the new line character, and
include the Replace With \\ to search for the backslash. Just type these codes in the Look For
text box.
text box, along with any other text. For example, type \tThe to find
the word The at the beginning of a paragraph.
As you can see, this dialog box includes three check boxes:
• Match Words: If you check this, the search looks for an exact
match only, and will not find a word that has the word you
are looking for embedded in it. For example, if you search for
top, it will not find stop or estoppel.
310 MASTERING FOXPRO
CH. 8
Replace With:
• Wrap Around: If you check this, the search will look from the
location of the cursor to the end of the file, and then will
“wrap around” and continue the search at the beginning of
the file. This option lets you search through the entire file
without first moving to the beginning of the file.
If you want to replace the text you are searching for with some
other text, type the new text in the Replace With text box. This
replacement is not made automatically, however; you must also
select one of the following options from the Edit menu in order to
make the replacement.
FIND AGAIN
Selecting Find Again from the Edit menu repeats a search you just
made without your having to fill out the dialog box again. This comes
in quite handy since files usually have the word you are looking for
more than once, and the first one you find is not necessarily the one
you want.
GETTING THE MOST FROM THE MENU SYSTEM 311
REPLACE ALL
Selecting Replace All from the Edit menu replaces every occur¬
rence of the text in the Look For text box with the text in the Replace
With text box.
PREFERENCES
Selecting Preferences from the Edit menu calls up the Preferences
dialog box, which lets you change the default settings of the editor. As
you can see from Figure 8.11, the default settings are different for
text, program, and memo windows. When you read the descriptions
of this dialog box’s features, look at these illustrations and note that
some of them are not available for all types of windows.
The default settings are usually the settings you need for the type of
file you have chosen. For example, if you are creating a text file, you
ordinarily want to have a word-wrap feature, so that the right margin
automatically determines where to break a line without you having to
keep track of where the margin is. If you are creating a program file,
though, you need to keep each command on its own line and press
Enter at the end of each command, so that FoxPro knows when the
command is complete, even if that means going beyond the visible
right margin for some commands.
FoxPro’s word-wrap defaults are set accordingly. If you create a
new text file, the Wrap Words check box of the Preferences dialog
box is automatically checked. If you create a new program file, it is
automatically not checked. You do not even have to look at the dialog
box; just type and you will find that these defaults are in effect.
312 MASTERING FOXPRO
CH. 8
I
[X] Wrap words Tab size: K
[X] Auto indent
[X] Make backup [ 3 Use these preferences
[X] Add line feeds as default for files
with no extension
[ ] Ctrl-Z sensitive [ 3 Save preference
1
[ Wrap words Tab size: K1
[x; Auto indent
[X] Make backup [ 3 Use these preferences
[X] Add line feeds as default for .PRG
[ : Compile when saved files
[ Ctrl-Z sensitive [ 3 Save preference
(• ) Left justify
( ) Right justify
( ) Center justify « OK » <Cancel>
H
[X ] Wrap words Tab
[X Auto indent
[ 3
as default for Memos
(• ) Left j ustify
( ) Right justify
( ) Cente:r justify « OK » <Cancel>
Figure 8.11: The Preferences dialog box with the default settings for text,
program, and memo files.
GE TTING THE MOST FROM THE MENU SYSTEM 313
CH. 8
for these three types of file: this check box is useful for people who do
not use more than one or two of these file types.
The check box marked Save Preference can be used more freely. If
you check it, these preferences will be used every time you edit this
file. The size and location of the window and location of the cursor
will also be the same as you left them the last time you closed the file.
ADVANCED TECHNIQUES
FOR MANIPULATING DATA -
APPEND FROM
Selecting Append From from the Database menu calls up the
Append From dialog box, shown in Figure 8.12. This dialog box lets
you add records to the currendy open database from another file.
GETTING THE MOST FROM THE MENU SYSTEM 315
To choose the hie to append records from, type its name to the
right of the From text button—or, if you do not know its name, select
the From text button to select it from a list of hies.
As you can see, this dialog box has Scope, For, While, and Fields
check boxes, which you are very familiar with from Chapter 5 of this
book. You can use these check boxes in the ways you have learned, to
determine which records to append from the selected hie to the cur¬
rently open hie. For example, to append only those with addresses in
California, you would check For and enter the logical expression
STATE = “CA”.
The Type popup of this dialog box is particularly useful, since it
lets you append records from other types of hies besides database
hies. Select this popup control and you will be given these choices:
CH. 8
TOTAL
Selecting Total from the Database menu calls up the Total On dia¬
log box, shown in Figure 8.13. This dialog box lets you compute
totals for the numeric fields in the current database and create a new
database file with corresponding fields to store the answers.
The key to understanding how Total works depends on the fact
that you must enter a field name or expression to the right of the Expr
text button. You can do this by selecting a field name from the scroll¬
able list, by selecting the Expr text button to call up the expression
builder, or simply by typing the field name or expression to the right
of this text button. The command then finds numeric totals based on
this expression. For example, if you select STATE, the new database
that is created will include totals for each state.
For Total to work, the database must be sorted on this same key
field or expression, or it must be in use with an index based on this
same key field or expression as the major index that determines the
order of its records.
GETTING THE MOST FROM THE MENU SYSTEM 317
The check boxes in the Total On dialog box are optional. The
Scope, For, and While check boxes let you limit the records that are
included in the total, in the ways that you learned in Chapter 5; and
the Fields check box lets you limit which fields are totaled. If you do
not use the Fields check box, all the numeric fields in the database will
be totaled.
The Save As text button displays the familiar Save As dialog box,
so you can type in a name for the new file. Of course, you can also
H As before, these
commands are
simply enter the name next to this text button.
Because of the preparation it requires, it is often more convenient
to perform this operation from the Command window. Use the fol¬
written using the usual
conventions: the parts of lowing command:
the command that are in
square brackets are TOTAL ON < field expression > TO <file name> [FIELDS
optional.
<fieldlist>] [FOR <logical expr>] [WHILE <logical expr>]
(all on one line, of course). You can prepare to use the command by
indexing first, for example:
USE EMPLIST
INDEX ON STATE TO STATES
TOTAL ON STATE TO EMPTOTAL
318 MASTERING FOXPRO
CH. 8
It is probably easier to create the index and then total from the com¬
mand line than it is to use the menu system for the same task.
In the following short exercise you will create and print a couple of
different variables. You will notice that, when you assign a value to a
variable, the value is displayed as FoxPro talk (unless you have set
Talk off). When you print the variable, the number includes leading
blanks. As you learned in Chapter 4, you can control its width and
number of decimal places by using the STR() function.
? (MVAR1 * 2) - (MVAR2/2)
CH. 8
AVERAGE
Both this Average Selecting Average from the Database menu calls up the Average
command and the dialog box, shown in Figure 8.15. This dialog box lets you find the
AVG() function give you
the arithmetic mean, which
average value for numeric fields or expressions in your database and
is calculated by adding a store the answer in memory variables.
list of numbers and divid¬
ing the sum by the num¬
ber of numbers in the list.
This is the most common System File Edit Database Record Program Window_
use of the word average,
which is sometimes used
in other senses.
Average: Memory Variables:
« OK »
To Variable:
If you select the Expr check box in this dialog box, you can enter a
field name or field expression for the command to average: for
example, enter WAGE to find the average wage. You can use only a
numeric expression with this command. If you do not enter an
expression, the command will average every numeric field in the cur¬
rent database.
The averages are displayed on the screen, as part of the FoxPro
talk (unless, of course, you have set Talk off).
If you enter an expression to average on, then you can also enter
the name of a memory variable to hold the result. You can create a
new memory variable by entering its name in the To Variable text
box. Or you can store the result in an existing memory variable,
replacing its current value, by selecting its name from the Memory
Variables list.
Ordinarily, you will get the average of all the records in the current
database file. You can restrict the records that are averaged, though,
by selecting the Scope, For, or While check box—for example, if you
want the average wage for one state.
You can use similar options from the Command window using the
AVERAGE command. The basic syntax is AVERAGE Knum expr>
[TO Kmemvar>]. The <memvar> in the optional TO clause of
course indicates the name of the memory variable. You can also add
a Scope or a FOR or WHILE clause before TO <.memvar>. For
Remember that, as
more details, see Appendix C.
you learned before,
all of these commands
include records that are
COUNT
marked for deletion
unless you use the com¬ Selecting Count from the Database menu calls up the Count dia¬
mand SET DELETE
log box, shown in Figure 8.16. This dialog box lets you count how
OFF before you execute
them, or use one of the many records there are in the current database.
other methods of dealing As you can see by comparing the illustrations, Count is very simi¬
with deleted records that
lar to Average, except that it does not have an Expr check box. This is
you learned in Chapter 5.
This is not only impor¬ because you do not need an expression to count on: FoxPro simply
tant when you are count¬ counts each record once.
ing records but also when
Like the Average, the Count of records is displayed as part of the
you are summing, aver¬
aging, and performing
FoxPro talk. You can store it to either a new or an existing memory
other calculations. variable in the same way, and you can restrict the number of records
322 MASTERING FOXPRO
CH. 8
« OK »
To Variable:
in the same way by using the Scope, For, or While check box. (The
usual check boxes are included even though you obviously would
never want to use Count with a Scope.)
You can use similar options from the Command window using the
COUNT command. The basic syntax is COUNT [TO Kmemvar^].
You can also add a Scope or a FOR or WHILE clause before TO
<memvar>. For more details, see Appendix C.
SUM
Selecting Sum from the Database menu calls up the Sum dialog
box, shown in Figure 8.17. This lets you find the sum of numeric
fields or expressions in your database and store the answer in mem¬
ory variables.
As you can see by comparing the illustrations, Sum works in a way
that is identical to Average. By default, it sums all numeric expres¬
sions and displays the result as talk. You can check the Expr check
box to enter a numeric expression to be summed (such as WAGE),
and you can store the result in a new or existing memory variable.
Select the Scope, For, or While check box to restrict the records that
are summed. From the Command window the basic syntax is SUM
GETTING THE MOST FROM THE MENU SYSTEM 323
« OK »
To Variable:
CALCULATE
Selecting Calculate from the Database menu calls up the Calculate
dialog box, shown in Figure 8.18. This dialog box lets you perform a
number of different calculations.
This dialog box works just like the others you have looked at, with
one exception: to use it, you must select the Expr text button. This
calls up a special version of the expression builder dialog box, which
has only the Math popup control and only a limited number of
options available, as shown in Figure 8.19.
Note that some of these calculation functions are used with no expres¬
sions, some require numeric expressions, and some (indicated by just
<exp>) can be used with numeric, character, or date expressions.
CH. 8
« OK »
To Variable:
Math
REPLACE
There is one very useful option on the Record menu popup that
you have not yet learned. Selecting Replace from the Record menu
lets you replace the value in a field of the current database with some
new value.
This option is very useful when it is used with the scope of ALL: it
lets you change or fill in a given field in every record in the database.
For example, say that you modify the structure of your database to
add a new logical field, and that the field should start off by being true
for every record: instead of using the keyboard to type the entry in
each record, you can use Replace with the All check box.
The default scope for Replace is NEXT 1; so if you do not specify a
scope it only replaces the value of the current record.
The Replace dialog box, shown in Figure 8.20, is easy to use. Just
select the field whose value you want to change (from the scrollable
list of field names), and type the new value to the right of the With
text button.
326 MASTERING FOXPRO
CH. 8
SETTING COLORS
There is one remaining command that you should look at briefly.
Selecting Color from the Window menu calls up the color picker dia¬
log box, shown in Figure 8.21. This dialog box lets you control the
colors of your FoxPro display—or, if you are using a monochrome
monitor, the intensity of your display. This command is not often
needed; it is useful mainly if you have an unusual color monitor that
is hard to read when FoxPro’s default colors are used.
ftmmi r* foVI'luh
s tA/ a<c *rr*A*
-t
X X X X X X X X X
X X X X X X X X X
X X X X X X X X X «
X X X X X X X X X [X] Shadow
X X X X X X X X X
X X X X X X X X Ej [ ] Blink
X X X X X X X X E
X X X X X X X X E
CH. 8
<’/>£€/Ff £ C&tof CP/WfitNAf'/ off
*Pb vjfW
F: &A fi,
foil fat
You can change the colors of many different features of your dis¬
*9
VPf f //[ £ play. The popup control in the upper right of this dialog box gives
you these choices:
r &M hi
' ■'
..
iiiisitis
To use the Fox View Shell, 337
press the Scroll Lock key to call up the Shell any time you are
using Fox View. The Shell has a prompt similar to the DOS
prompt, where you enter commands.
CH. 9
If you find that you Fortunately, you do not need to know anything about FoxCode in
do not have any order to use FoxView. Several templates have already been created
templates available when
and compiled and were automatically put in a subdirectory named
you use FoxView, see
Appendix A on installing \FOXPRO\TEMPLCOD when you installed FoxPro. You can
FoxPro, which includes simply use them to generate applications. You should have these
installation of these tem¬
templates:
plates. If necessary,
reinstall FoxPro following
the instructions from the • ADVANCED: An advanced database-maintenance applica¬
beginning. tion, including popup menus. Though it is much simpler
than FoxPro itself, this application is complex enough that it
requires a bit of learning before it can be used.
If you have a later release of FoxView, you may have more tem¬
plates available. We can expect developers to come up with more
templates in the future, and many will probably be public-domain
software or shareware. In this way FoxView will become more and
more powerful.
336 MASTERING FOXPRO
CH. 9
• File View: Press F9 to use File View, which gives you sum¬
mary information about the files you are using.
CREATING CUSTOM DATA-ENTRY SCREENS AND APPLICATIONS 337
In addition, you can press FI at any time to get help with Fox View
(as with FoxPro). Help is context-sensitive: the help screen that
appears describes the feature that you were using when you pressed
FI. You can then use PgUp and PgDn to scroll through all the help
screens. Press Esc to exit from the help system.
CH. 9
a In some early
releases of FoxPro,
ily if do you want to use it.
2. Press FI, the help key, and glance at the first help screen for
the Shell, shown in Figure 9.2, with the headings Navigation
Keys and DOS Commands.
3. Press PgDn to see the second help screen for the Shell, shown
in Figure 9.3, with the heading Database Commands.
CREATING CUSTOM DATA-ENTR YSCREENS AND APPLICATIONS 339
NAVIGATION KEYS;
1 <Uparrow>-<Downarrow> ft
Scroll to previous/next command
2 <PgUp>-<PgDn> ft
Scroll to previous/next page
3 . cCursor keys> ft
Command line navigation
4 . LIST HIST[ORY] ft
List command-line history
DOS iCOMMANDS:
1 . <d : > ft
Change disk drive
2 . CD <pathname> ft Change directory
3 . CLS ft
Clear screen
4 . COPY (source) <dest> * Copy file from source to dest
5 . DIR <filespec> [/W] * Directory listing
6 . ERASE <filespec> ft
Erase file
7 . MD <pathname> ft
Make directory
8 . PATH ft
Display current PATH
9 . RD <pathname> ft
Remove directory
10 REN (source) <dest> ft
Rename source to dest
1 1 . TYPE <filespec> ft
Display file contents
DATABASE COMMANDS:
1 . APPEND < fn > [ALIAS < C >] * Append DATABASE or text file
2 . CREATE < fn > [alias <c>] * Create database file
3. IMPORT < fn > [ALIAS <c>] * Import @/SAY/GET/PICTURE/RANGE
4 . LIST [ALIAS <c >] * Display current structure
LIST * . dbf * Display database structures
LIST *. idx * Display index keys
CH. 9
4. Press PgDn to see the third help screen for the Shell, shown in
Figure 9.4, with the heading Shell Commands.
Fox View stores the last commands that you have entered, up to a
maximum of 36 commands, and these are sometimes called the com¬
mand history. The navigation keys on the first help screen are meant to
let you scroll through these commands so you can reuse them. Just press
the up and down arrow keys or PgUp and PgDn to move through the
command history. Then you can reenter previous commands.
SHELL COMMANDS:
1 . <filename> [<parms>] * Run .COM, EXE, or ,0A1 file
2 . CONFIG <filename> * Load new CFG file
3. EJECT * Elect printer page
4 . EXIT * Exit to DOS
5. LIST ST AT[US] * Display flags and system status
6 . QUIT * QUIT FoxView
7. RUN <filename> [<parms>] if Run .COM, .EXE, or .BAT file
8. SAVCAP <filename> * Save 4000-byte screen image
SAVTXT < filename> * Save only text portion
• PATH displays the current search path, the list of all the sub¬
directories that DOS looks in for commands that you enter.
342 MASTERING FOXPRO
CH. 9
• LOAD <file name> lets you use a FoxView table that you
created and saved at an earlier time.
• NEW <file name > clears FoxView of the screen you are cur¬
rently using and lets you begin work on a new screen. After it
is used, a dummy field called Noname is created, which can
be modified or deleted.
• SAVE <file name> saves the FoxView table that you are cur¬
rently working on.
• VIEW FILE lets you use the File View feature of FoxView,
which you can also access by pressing F9.
• VIEW FORMS lets you use the Forms View feature of Fox¬
View, which you can also toggle by pressing F10.
• VIEW TABLE lets you use the Table View feature of Fox¬
View, which you can also toggle to by pressing F10.
344 MASTERING FOXPRO
CH. 9
The third help screen includes utilities that sometimes make it eas¬
ier to use FoxView.
• QUIT quits FoxView and returns you to FoxPro (if you ran
FoxView from FoxPro) or to DOS (if you ran FoxView as a
stand-alone program).
1. Press Esc to leave the help system and return to the Shell.
2. Press Esc to access the menu system. There are only four
choices on the menu bar, which you can move among by
using the left and right arrow keys. Use the arrow keys to
move to the Disk popup of the menu. Then press the right
arrow key to move among the other popups as you read the
descriptions of them below.
Not all the features of the menu system are essential: the most impor¬
tant are summarized at the end of this section.
The Disk popup, shown in Figure 9.5, includes the following
options:
• Directory: returns you to the Shell and lists the files in the cur¬
rent subdirectory. You may use a file name or a file name with
346 mastering foxpro
CH. 9
Caps-Ins
Press the right arrow key to see the Load popup, shown in Fig¬
ure 9.6, which includes the following options:
5 Though FoxView
has such features as
• Current Alias: like the SELECT command that you have
used in FoxPro, changes the current work area. As you will
Current Alias to let you
see, you can also do this by moving the highlight in File
work with related files, it
is not really suitable for View, which lists all the work areas and open files.
working with relational
databases—as you will
see when you read the
next section, on Field Disk I Load Gen Fields JE : 16 a
R5
View. FoxVi Current Alias “TT
Load Table { . fV }
Save Table NONAME
Caps-Ins
• Load Table and Save Table: are used to work with the tables
that you create with FoxView. You will see in the section on
Forms View and Table View that these tables record the fea¬
tures of the custom screen that you design. Save Table lets you
save the features of the custom screen; Load Table lets
you work with a custom screen that you have designed at an
earlier time.
CH. 9
Now press the right arrow key to move to the Gen popup, shown
in Figure 9.7. This is the working popup that you use to generate
programs.
• Select From Template List: lets you choose the template to use
from a menu of all the templates in the specihed directory.
CREATING CUSTOM DATA-ENTRYSCREENS AND APPLICATIONS 349
► SET COLOR TO
► Products
Caps-Ins
• Author and Copyright: let you enter the name of the program
author and copyright holder of the programs you generate
using FoxView, which are included in the programs before
the code begins (though they do not appear on the screen). If
you entered your name and company name when you
installed FoxView, they are entered as the default values
here, and you can use these options to change them.
Press the right arrow key to move to the Fields popup, which is
shown in Figure 9.8. This popup controls relatively minor features of
the screen display and is not essential to using FoxView:
Fill Char: lets you fill the spaces between the field labels and the
fields themselves with some character, for example, with dots.
m
Disk Load Gen 10 16 a!u
FoxView C:>
Caps-Ins
• Height of Box and Width of Box: control the default size used
for drawing boxes. As you will see, boxes are easy to resize,
and there is not much need to worry about their default size.
If you look back over all the features of the menu system, you will
see that only a few are needed to start working with FoxView. To
make it easier for you to get underway, the essential features are
listed below:
• from the Load menu: Use Datafile, Load Table, and Save Table
to create, use, and save FoxView custom screens
CREATING CUSTOM DATA-ENTRY SCREENS AND APPLICATIONS JJ 7
• from the Gen menu: Select From Template List to select the tem¬
plate that you want to use to generate the program
If you go back and review these features in the lists above, it will be
easy for you to find your way around the menu system while you are
working.
FILE VIEW
Before looking at File View—and before looking at Forms View
and Table View in the next section, you should use your EMPLIST
database:
1. Use the arrow keys to move to the Load popup. Select USE
Datafile. A prompt will appear on the bottom of the screen
with the name of the current directory followed by the file
name NONAME.DBF. Press End; then press Backspace to
delete this file name, but be careful not to delete the directory
name or the backslash immediately preceding the file name.
Then type EMPLIST. as the file to use; its name will appear
on the menu popup as you type. Press Enter to use the file.
The Database and Alias screens of File View look very impressive,
since they let you keep track of multiple database files and set relations
between them. Unfortunately, FoxView supports only one-to-one rela¬
tions and not one-to-many relations; so it cannot be used to generate
code for true relational databases. As you learned in Chapter 7, if data
has a one-to-one relation, it is best to put it into a single file.
In practice, in most applications, FoxView’s File View feature just
serves as a simple reminder of basic facts about the file you are using.
352 MASTERING FOXPRO
CH. 9
- ~r ~ “T
l _ TTTTTJ
r
ITTT TT UA1ADMol FILES n TT n
TT V It 1 TT n
-
Als Datafile Allas User DBT Fids Recsiz Ndxs Reis Updated _
_ niTiiii rrn m j nil n mi rim i itttm t iiii i i iiii in..i 11111 n n m m biiill
Caps-Ins
C:\LEARNFOX\EMPLIST.DBF
FoxPro database file
C : EMPL1ST.DBF 10:17
■ j';
M L _L M o M
- 1
• F3: lets you drag (move) the selected object by using the
arrow keys
• F4: lets you resize the selected object by using the arrow keys
(which is useful primarily for boxes)
• Ctrl-U: deletes the selected object (after asking the user for
confirmation)
• Ctrl-B: adds a box object, which you may then drag and
resize
You use these keys to change the screen in Forms View, to “paint” it
with the data-entry form you want.
Table View is a tabular description of the screen shown in Forms
View: the data in the table changes as you change the form. In addi¬
tion, Table View has columns that let you validate data, as you will
see. Before quitting FoxView, you can save the table.
When you start work with FoxView, you can either use a database
file or load a table that you have previously saved; both of these can be
done with the menu system. If you use a database file, FoxView auto¬
matically creates a standard form for it (which looks like the usual
Change or Append window) and a table that summarizes this standard
form; you begin designing your custom screen from this point. If you
354 MASTERING FOXPRO
CH. 9
load a table that you saved, of course, Fox View displays the correspond¬
ing screen and lets you begin your design work from this point.
Empno
Fname
l name
Address
Apt_no
City
State
Zip
Date_hired
Wage
Probation
Notes
Caps-Ins
C:EMPLIST.DBF
#. Als Field Typ Wid Dec Label Hue Row Col Pag (Fid)
BPf
(Atr) Place
1 . A Empno | C 3 [Empno A 2 0 1 GET 112 SIDE
2. A Fname c 13 [Fname 4 3 0 1 GET 112 SIDE
3. A Lname c 20 [Lname 4 4 0 1 GET 112 SIDE
4 . A Address c 25 [Address 4 5 0 1 GET 112 SIDE
5. A Apt no c 5 [Apt no 4 6 0 1 GET 112 SIDE
6 . A Ci ty w 20 [City 4 7 0 1 GET 112 SIDE
7. A State c 2 [State 4 8 0 1 GET 112 SIDE
8. A Zip c 5 [Zip 4 9 0 1 GET 112 SIDE
9. A Date hired D 8 [Date hired 4 10 0 1 GET 112 SIDE
10. A Wage N 5 2 [Wage 4 11 0 1 GET 112 SIDE
1 1 . A Probation L 1 [Probation 4 12 0 1 GET 112 SIDE
12 . A Notes M 10 [Notes 4 13 0 1 GET 112 SIDE
pan
Uapo Tno
XII q
Advanced FoxView users can edit the Table View screen. The
only features of Table View that are useful for beginners, though, are
those concerning the validation of data. For example, if the user
enters data that does not match the criterion, you can have FoxPro
beep and refuse to accept the entry.
Rather than memo¬ The Picture column lets you enter a picture template, similar to
rizing these picture
those you used to format report fields in Chapter 6 (and summarized
templates, use the Fox-
View help facility: just in Table 6.2). Figure 9.13 shows the FoxView help screen for entries
press FI when the cursor that you can make in the Picture column.
is in the Picture column.
Most picture templates screen out invalid data: for example, 9
At this point, all you need
is a general idea of what accepts only digits. Some convert data: for example, ! converts a char¬
picture templates can do; acter to uppercase. You can also use literals in picture templates—for
you do not need to learn
example 999-99-9999 for the entry of Social Security numbers. Repeat
the exact symbols and
syntax.
the symbol as many times as you want the character to be entered (for
example, X99 lets the user enter an employee number comprising a
letter followed by two digits) or use the symbol @ before the symbol to
indicate that it is repeated an indefinite number of times (for example,
@! capitalizes any number of characters entered in the field). Tem¬
plates that begin with @ are sometimes called function templates. Pic¬
ture templates and function templates will be discussed in more detail
in Chapter 10. ,
356 MASTERING FOXPRO
CH. 9
110 18 a rti
—-r--- -Caps-Ins
GENERA TING
A CUSTOM DATA-ENTRY FORM _
After this introduction to FoxView, it should be easy for you to
become accustomed to using this program by doing a couple of
exercises.
First, you will learn to create custom data-entry forms. You will
begin with the standard form, which looks like the FoxPro Append
window. Then you will rearrange the fields of the database file so that
they are easier for the user to understand, change the field names to
more descriptive names, add instructions that tell the user exactly
CREATING CUSTOM DATA-ENTRY SCREENS AND APPLICATIONS 357
what to do, and include graphic characters such as boxes to make the
D To return to the
usual Append or
screen easier to grasp.
The format screens that FoxView generates are meant primarily to
2. If you have not yet loaded the EMPLIST database hie, the
screen will have only one held, called NONAME. To load the
database hie, press Esc to use the menu. From the Load popup,
select USE Datafile. FoxView displays the current name of the
hie at the lower left of the screen: the full path name, ending
with NONAME.DBF. To edit it, press the End key, then press
Backspace until you have erased the current hie name, NO¬
NAME. DBF, but not the backslash before it; then type
EMPLIST and press Enter. (FoxView assumes the .DBF
extension.) The screen now looks like Figure 9.14, with the
helds arranged in much the same way they are in FoxPro’s
Change window.
358 MASTERING FOXPRO
CH. 9
3. Edit the labels of the fields to make them more explicit. The
word Empno has a flashing cursor under it to indicate that it
is selected. Press the space bar to edit this label: the cursor
appears on the edit line at the bottom of the screen. Press the
right arrow key three times to move the cursor to the n in
Empno, and type loyee followed by a blank space. Notice
that, as you type, the label changes on the screen above.
Then press the right arrow key to move the cursor to the o of
no, and press the Ins key to toggle to typeover mode. Type
umber, and press Ins again to toggle back to insert mode.
Press Enter to stop editing and return the cursor to the label
on the screen above.
4. Press the down arrow key to move the cursor to the next field
name, Fname, and press the space bar to edit it. Change it to
First name. Notice that there are a number of blank spaces
between the label and the field in the screen above: press End to
move to the end of the edit line, and you will see that the blanks
are there too. Press Backspace to remove all these blank spaces
except one, and then press Enter.
5. Go through all the field names in the same way. Edit them to
remove unnecessary blank spaces, so there is just one space
CREATING CUSTOM DATA-ENTRY SCREENS AND APPLICATIONS 359
Ins
7. The screen still looks more cluttered than it was before, but
now you are ready to rearrange the helds to make it easier to
read. Move the cursor to Last name and press F3 to drag it:
notice the help line at the bottom of the screen, shown in Fig¬
ure 9.16. Follow its instructions to rearrange the helds to look
like the screen shown in Figure 9.17. For example, press the
right arrow key to drag the held until it is at the right edge of
360 MASTERING FOXPRO
CH. 9
Employee number
First name
Last name
Address
Apartment
City
State
Zip
Date hired
Wage
Probation? (t/f)
Ins
Figure 9.16: The help line tells you how to drag a field.
Employee number
Address Apartment
Ins
the screen: line up its right edge with the right edge of the
time display, which is in the upper right corner of the screen.
Press Enter to stop dragging and to keep it there. Use the
same method to rearrange the other fields as shown.
8. Press F10 to toggle to Table View. Note that the Row and Col
numbers in the table have changed to reflect the new positions
of the fields, and that the labels have changed, even though the
field names remain the same, as shown in Figure 9.18. Notice
also that the Notes field has been removed from this view as
well. Press F10 to toggle back to Forms View.
C:EMPLIST.DBF
#. Als Field Typ Wid Dec Picture Range Valid Inlt Calc User
1 A Fmpno C 3 [ [ H [ ][
2. A Fnamo C 15 [ L ][ [ ][
3. A L name C 20 [ t JL [ ][
4. A Address C 25 [ [ JL [ ][
5. A Apt_no C 5 r t ][ [ ][
6. A City C 20 i: [ H [ ][
7. A State C 2 r [ J[ [ ][
8. A Zip C 5 f [ ][ [ ][
9. A Date_hired D 8 [ [ ][ [ ][
10. A Wage N 5 [ [ ][ [ ][
11 . HI Probation L 1 c [ ][ [ JL _
Ins
CH. 9
instructions, because you will use this same data-entry screen later in
this chapter for the menu-driven application, which has instructions
built in. In an actual application, of course, you could give more
elaborate help to the data-entry person.
The on-screen help that you add will consist of a few text objects
surrounded by a box:
1. Before adding help for the data-entry person, draw a box for
the help lines. Press Ctrl-B to call up the Select Box menu
popup. Press the down arrow key three times to select Box-
Stringl, and press Enter. The box is placed and is high¬
lighted to show that you can now drag it into place. Press the
down arrow key a few times, until it is below all the field
names, and the left arrow key until it is near the left margin,
and then press Enter.
5. Finally, center the help lines. Press Ctrl-C to center the cur¬
rent one. Press the up arrow key and then press Ctrl-C
to center the upper one. The screen should now look like
Figure 9.19.
CREATING CUSTOM DATA-ENTRY SCREENS AND APPLICATIONS 363
-Ins
VALIDA TING DA TA
That finishes the design of the data-entry screen. Now you can use
Table View to add picture templates to a couple of fields. As an exercise,
you will add picture templates to capitalize the first and last names as
they are entered and to make sure that only numbers are entered in the
zip code field. Remember that, in the early parts of this book, you
always had to worry about names that were added in small letters.
Though users were supposed to enter all the names in capital let¬
ters, there were inevitable errors, and you had to write your queries
using the UPPER() function to correct for them. In a program, it
makes sense to use the picture function to capitalize all the names auto¬
matically as they are entered, so that you do not need to allow for pos¬
sible errors in all the rest of your code.
You will also validate the amount of the wage. Assuming that the
wage must be between $4.00 and $50.00, you can add these figures
in the Range column of the Wage field, to make sure that the data-
entry person cannot enter wages that are outrageously incorrect.
You would probably do more validation in an actual application—
for example, you would probably want to capitalize more fields, to
give a range for the date hired, and to validate the employee number
364 MASTERING FOXPRO
CH. 9
2. Press the right arrow key, and then the down arrow key twice
to move to the Range column for the Wage field. Type 4,50
and press Enter. Figure 9.20 shows the Table View with
these entries. Now you can press F10 to toggle back to Forms
View: notice that there is no indication of the templates or
range you entered.
10 51 ai
u. Als Field Typ Wid Dec Picture Range Valid Init Calc User
1. A Empno C 3 [ ][ ][ ][ ][ ][ ]
2. A Fname c 15 [®! ][ ][ ][ ][ H ]
3. A Lname c 20 [#! ][ ][ ][ ][ ][ ]
4. A Address c 25 [ ][ ][ ][ ][ ][ ]
5. A Apt no c 5 [ ][ ][ ][ ][ ][ ]
6 . A City c 20 [ ][ ][ ][ ][ ][ ]
7. A State c 2 [ ][ ][ ][ ][ ][ ]
8. A Zip c 5 [99999 ][ ][ ][ ][ ][ ]
9 . A Date_hired D 8 [ ][ ][ ][ ][ ][ ]
10. A Wage N 5 2 [ ■114,50 |][ ][ ][ ][ ]
11 . A Probation L 1 [ ][ ][ ][ ][ ][ ]
12 . A BOXOBJECT B 72 4 [ ][ ][ ][ ][ ][ ]
13 . A TEXTOBJECT T 32 [ ][ ][ ][ ][ ][ ]
14 . A TEXTOBJECT 1 58 [ ][ ][ ][ ][ ][ ]
Ins
4.50
RANGE: (lower exp>,(upper exp>; press FI for Help
Figure 9.20: Entries in the Picture and Range columns to validate data.
to create the format screen. Then you can quit FoxView and use Fox¬
Pro to test the screen.
1. Press Esc to access the menu. From the Gen popup, select
Select From Template List. The template list appears, as in
Figure 9.21. (Of course, yours may have added templates.)
Move the highlight to FORMS 1: Format File Generator and
press Enter. The program asks for the name of the file that
will be generated. Type DATAENTR and press Enter. The
program file scrolls by as it is created, and then the message
Program File(s) Created appears at the bottom of the screen.
Ins
B ln an actual applica¬
tion, you might
have more than one table Figure 9.21: The list of available templates.
for the same database file.
If so, you should choose
2. Before exiting, save the table in case you want to reuse and
descriptive names for
them all, rather than modify it at some later time. From the Load popup, select
accepting FoxView’s Save Table. FoxView will suggest the name EMPLIST.FV;
suggestion of using the press Enter to accept that name. Now, from the Disk popup,
file name for the name of
select QUIT FoxView and press Enter. Type y to confirm
the first table. When you
enter a new name, it is that you want to quit and to return to FoxPro.
not necessary to add the
.FV extension: FoxView
3. Use the EMPLIST file by selecting Open from the File
assumes it. menu, and then when the Open dialog box appears, select
366 MASTERING FOXPRO
CH. 9
4. If you want, you can try paging through the database or adding
records using the custom screen. As a test, move the cursor to
Zip and try entering the letter g. FoxPro will beep, as the tem¬
plate you have implemented allows only numbers. Move the
cursor to Wage. Type 60 and press Enter. FoxPro beeps and
displays an error message saying you are out of Range.
Employee number
Address Apartment
As you can see, once you have done the work of designing the
screen, generating the program is easy.
CH. 9
maintain the database and produce reports and mailing labels simply
by making the appropriate menu choices.
2. First, you must use the table you created earlier. Press Esc to
use the menu system. From the Load popup, select Load
Table. The prompt appears at the bottom of the screen: enter
the name EMPLIST. (FoxView assumes the .FV extension.)
3. Now, you can generate the application. From the Gen popup,
select Select From Template List. When the list appears, se¬
lect APPS1: File-Maintenance Application. FoxView will ask
for the name of the program it should generate. Enter EM¬
PLOYEE. When FoxView asks if you want Special Features,
type n. When it asks about modules, type n. When it asks for
menu style, select Simple. When it asks for submenu style,
select Bracketed. The code scrolls by as it is generated. Notice
that a number of programs are created, each with the same
heading at the top (including your name, if you entered it when
you installed FoxView). Finally, FoxView displays a message
saying Program Files Created.
0. Quit
1 . Append
2. Browse
3. Edit/View
4. Help
5. Labels
6. Pack
7. Report
U=- select : : -
CH. 9
Employee number an
that you created earlier. You could also use the application genera¬
tor, though, if you were called in as a developer to create a database
system from scratch. Then you would have to do the more difficult
job of analyzing the user’s needs, and of designing the database file,
data-entry screen, and report and label forms accordingly. When
you do this sort of thing, you are almost a programmer, since analyz¬
ing the system’s requirements in this way is often the most difficult
part of programming.
Many modules that
In the next chapter, you will begin doing actual programming. If
FoxView generates
begin with the first three
you want to get more experience with the application generator first,
letters of the application ■ try selecting the ADVANCED template (just as you selected the
name, as in EMP_EDIT APPS1 template in this section) to generate an application with pop¬
and EMP_PACK. So
these files are not over¬
up menus. But give the program a different name, so the files it
written, make sure the creates do not overwrite the files in the EMPLOYEE application you
name of the new applica¬ just created. You will see that the data-entry screen you have
tion begins with different
designed looks awkward in combination with pop-up menus, and
letters than EMP.
you might want to design a new one.
hapter 10
Expanding Your Capabilities
through Programming
To write a structured program, 378
break down the program into separate modules (or procedures)
and use only three types of control flow: sequence, selection,
and iteration (or looping).
CH. 10
STRUCTURED PROGRAMMING -
Apart from the ease with which it can be used to create useful
applications, FoxPro is a good introduction to computer program¬
ming because it is a structured programming language.
EXPANDING YOUR CAPABILITIES THROUGH PROGRAMMING 379
CH. 10
CH. 10
There are a few preliminary details that you should know before
you write your first sample programs in the next section.
Programs are plain ASCII text files, which can be created with
most text editors or with word processors that create plain ASCII files
(which some word processors call DOS files).
FoxPro and other dBASE compatible languages require you to
start a new line for each line of programming code: the new line is the
delimiter that lets FoxPro know where a single command begins and
ends. For this reason, you cannot use an editor with a word-wrap fea¬
ture that breaks up a line simply because it reaches the right margin.
Without word-wrap, you can simply keep typing the code beyond the
EXPANDING YOUR CAPABILITIES THROUGH PROGRAMMING 383
right margin. (If you select New from the File menu and then select
the Program radio button, or if you enter the command MODIFY
COMMAND <file namey, the FoxPro editor will have its word-wrap
a A semicolon within
a character string
feature turned off.)
If you want to be able to read your code more easily, you can keep
it from going beyond the right margin; you can break a long line in
will not break the string.
If you need to break a two by adding a semicolon (;) at the place you want it to break. This
line at a point where you will make FoxPro ignore the indication that the next line is a new
are in a character string,
line, and read the two lines as a single command. Of course, the list¬
you can break the string
into two strings at that ings in this book will use ; to fit the command in the width of the page.
point and use the semi¬ When you see this character, you can either type the code as it is in
colon followed by the plus
the printed listing, or you can leave out the ; and continue typing the
(+) sign. Don’t forget
that each string must be code on a single line.
enclosed in quotation The FoxPro interpreter ignores extra blank spaces. You can skip
marks. lines, and add extra blank spaces or tabs whenever you think that will
make the program easier to read. When you break a line in two using
the ; character, for example, it is good to indent the second line to
make it clear that it is a continuation of the same command. Like¬
wise, as you will see, indentation is very important in making it easier
to understand a program’s control flow.
Programs should also contain comments, which are used solely to
make it easier for people to understand the program. The program
itself does not use the comments.
FoxPro includes three commands that let you add comments. An
asterisk * or the word NOTE at the beginning of a line signals FoxPro to
ignore everything on that line. Using an asterisk at the beginning of the
line is the most common way of adding comments. It is also a good idea
to add a few hyphens after the asterisk: though they are not required,
they make the comments stand out so they are easier to follow.
The symbol && is used to add comments to the right of your pro¬
gramming code (rather than on a separate line). This double amper¬
sand may be used anywhere in the line. FoxPro executes the
command to its left, and ignores only the text to its right.
Programs are often difficult to follow when you come back to them
after not working with them for a year. The logic that seemed so obvi¬
ous to you when you were writing the program suddenly seems mys¬
terious: it is hard to figure out what you were doing. For this reason,
384 MASTERING FOXPRO
CH. 10
it is good to write a comment before each major activity that the pro¬
gram performs, identifying what the program is about to do.
The command SET You can run a program by entering DO <program name"> or by
ESCAPE OFF
selecting Do from the Program menu and selecting the name from
disables the Esc key so
that you cannot use it to the scrollable list. You can stop a program from running by pressing
stop a program. You can Esc. When you do this, FoxPro displays an alert that gives you three
add this command to the
choices:
beginning of a program
you have created, to keep
the user under your • Cancel: stops execution of the program permanently. This is
control at all times, but the default choice.
you should not add it
until after you have • Suspend: stops execution of the program temporarily and
finished your program¬ returns you to the Command window. You can start the pro¬
ming and debugging
gram again from the point where you left off by selecting
work, so you can use the
Esc key yourself. Resume from the Program menu or by entering the com¬
mand RESUME.
• Ignore: ignores the fact that you pressed Esc, and continues
execution of the program.
TALKING TO
THE USER: INPUT/OUTPUT _
The programs that you write to test input/output will use both of
these types of variable. You will begin by learning unformatted
input/output and then go on to learn formatted input/output.
CH. 10
? "Hello, "
?? "FNAME"
SET PRINT ON
? 'This line is going to the printer."
SET PRINT OFF
This command gets input from the user and creates a memory vari¬
able to store it in. If the optional character expression is included, that
character expression is used as a prompt. INPUT will keep repeating
the prompt until the user makes a valid entry.
You will have no trouble understanding how this command works
if you write a very simple program to test it. Before running this pro¬
gram, you should enter the command SET TALK OFF in the Com¬
mand window, so that FoxPro does not display talk to the screen and
disrupt the display that your program has set up. In an actual appli¬
cation, you would include the command SET TALK OFF in the pro¬
gram itself.
After running the sample program, you should change the listing
to add an error to it, so you can see how FoxPro helps you with
debugging.
CH. 10
The program list¬ dialog box lists all the existing .PRG files in its scrollable list,
ings in this book
including all the files that you generated in Chapter 9 using
follow the common pro¬
gramming convention of
Fox View. Enter TEST1 as the name of the new file, then
writing words of the select the default text button, Save. FoxPro automatically
FoxPro language in adds the .PRG extension. Close the Program window after
capital letters and writing
writing and saving the program.
variables and comments
in small letters. This is
merely meant to make
the program easier to •k-k'k'k-k’k-k'k'k'k-k'k'k'k-k-k-kick-k'k-k-k'k'k'k'k-k-kick-k'k'k-k
3. Enter SET TALK OFF (or select View from the Window
menu and use the View window to set the talk off).
5. If you did not have any errors in the program, try adding one
to get a demonstration of FoxPro’s debugging capabilities.
Edit TEST 1. PRG again and eliminate the final parenthesis
following the function that prints the age, so it now reads as
LTRIM(STR(m_ _age + 1), with unbalanced parentheses.
Save it in this new form and then run it. When you get to the
line with the error, FoxPro displays an error message plus the
program code with a highlight on the line that has the error,
as shown in Figure 10.4.
EXPANDING YOUR CAPABILITIES THROUGH PROGRAMMING 389
H Do Program File:
EMP_HELP.PRG Drive
EMP_LABE.PRG
EMP_MENU.PRG
EMP_OPEN.PRG
EMP_PACK.PRG Directory LEARNFOX
EMP_PHRA.PRG
EMP_PROC.PRG
EMP REPO.PRG « Do »
B1Q1
[ ] All Files
I
< Cancel >
Figure 10.2: Using the menu system to run the sample INPUT program.
CH. 10
TEST 1 .PRG
■******-*****w****»www*«w*-*w*w**ww-*ww
*TEST1.PRG
^sample program to illustrate the use of INPUT
***■#*■#*■#■*■#■**■*-**•-#*-#*#*#******-**-**•***
CLEAR
?
?
INPUT "How old are you? " TO m_age
7
|? "Next year you will be " + LTRIM(STR(m age + T)|
9
9
As you can see when you run the program, the character expres¬
sion “How old are you? ” appears as a prompt for the user; when
the user makes an entry, it is stored as a variable and then used by the
program as part of the next message to the user. A second INPUT
command is used to make the program pause so that the user has
time to read this message; because INPUT must save the user’s
response in a variable, this second occurrence of the command saves
the user’s choice in a memory variable named dummy because it is
never actually used. Notice that this program used ? to skip lines so
that this prompt would not be right at the top edge of the screen.
The major limitation of the INPUT command is that the data type
of the memory variable it creates is determined by the data type of the
user’s input. What this means is that, in order to use this command
EXPANDING YOUR CAPABILITIES THROUGH PROGRAMMING 391
to get a date or a character string, you would have to tell the user to
enter the data with the proper delimiters. To get the user’s name, for
example, you would have to use a command like:
Likewise, in TEST1, you had to have the user enter another number
to continue at the end of the program. INPUT does not cause any
trouble when you actually want to get a number, but it is not at all
user-friendly when you are working with other data types.
Because it is common to use an unformatted input/output com¬
mand to get text, there is another command that is like INPUT but
that reads any input as a character expression. The command
works very much like INPUT except that it reads whatever the user
enters as a character string. Unlike INPUT, which creates a memory
variable whose data type depends on what the user enters, ACCEPT
always creates a memory variable of the character type. If necessary,
you can then use the functions that you learned in Chapter 4 to use
this input as if it were another data type—VAL( ) for the numeric
type and CTOD( ) for the date type.
As with INPUT, the optional character expression that you use with
ACCEPT appears as a prompt for the user. Try a sample program to
test ACCEPT. The easiest way to create this program is by editing the
program you created earlier, then saving it under a new name:
3. Select Save As from the File menu. Save this program under
the name of TEST2. FoxPro adds the .PRG extension.
CH. 10
***********************************
*TEST2.PRG
*sample program to illustrate the use of ACCEPT
***********************************
CLEAR
7
7
ACCEPT "What is your name? " TO mname
7
INPUT "How old are you? " TO m_age
7
7
? "Sorry, " + PROPER(mname)
? "Next year you will be " + LTRIM(STR(m_age + 1))
7
ACCEPT "Press Enter to continue " TO dummy
"Z
Sorry, Charles
Next year you will be 40
There is one other input command that you will often find useful.
Both INPUT and ACCEPT require the user to type something and
then press Enter before the program continues. Often, there are
times when you want to let the user press just one key, without hav¬
ing to press Enter afterwards. To do this, use the command
Just the word WAIT, then, could substitute for the entire last line in
both of the previous programs. It would not only display the correct
prompt automatically but would also have the advantage of letting
the user press any key rather than having to press Enter.
The WAIT command is also useful to get a yes or no from the user.
For example, programs often include code like:
In cases such as
■■ this one, where the
WAIT "Do you want to print the report (y/n) " TO yesorno
memory variable is cre¬
ated, used immediately,
and discarded, program¬ This displays the prompt and creates a memory variable named
mers often do without the yesorno to hold the user’s response; the program can decide whether
initial m in the name of
or not to set the printer on depending on the contents of that variable.
the variable, as it is not
really required when the The advantage of using WAIT in this sort of situation is that it lets the
function of the variable is user make the choice with just one keystroke, without pressing Enter;
so obvious. though this feature might not seem too important when you read
about it, it can change the feel of a program entirely.
394 MASTERING FOXPRO
CH. 10
H Though it is most
common to use
commands, and more.
The basic form of this command is:
get the user’s input. The advantage of this is that you can write a long
series of @ . . . SAY . . . GET commands and then use READ just
once at the end to get the user’s input for all of them. Thus, rather
than just getting input one line at a time, as you did with unformatted
input/output commands, you can present the user with an entire
data-entry screen before getting any input.
Notice that the SAY and GET clauses in this command are both in
brackets, indicating that they are optional. It is most common to use
both clauses in a command. The variable that you GET will appear
just to the right of the prompt that you SAY. It is common, though,
to leave one of them out and use the command just to print a prompt
or just to get input without a prompt.
In general, the user must press Enter after each input. If the input
fills up the entire width of the field, though, FoxPro will beep (assum¬
ing that you have not set Bell off) and go on to the next field, just as it
does in ordinary data entry.
Try an example to get a feel for the basics of this command. Enter
the program listed in Figure 10.7 in a file named TEST3.PRG, then
compile and run it. Its output is shown in Figure 10.8. Notice the
three steps in this program: define the variables, use the command
@ . . . SAY . . . GET, use the command READ. Notice in particu¬
lar how much control the READ statements give you. You can deter¬
mine exactly how much is displayed on the screen when the user
inputs data. When you run this sample program, for example, the
final line does not appear on the screen until after the user has entered
the data in the earlier lines.
***********************************
*TEST3.PRG
*sample program to illustrate formatted input/output
***********************************
mcity = SPACE(15)
mstate = "CA"
mkey = " "
CLEAR
@ 12,0 SAY "Enter the city: " GET mcity
@ 14,0 SAY "Enter the state: " GET mstate
READ
@ 20,0 SAY "Press any key to continue... " GET mkey
READ
Perhaps you noticed that the program you just ran looked very
much like the data-input screens that you created in Chapter 9 using
FoxView. Format programs must be made up entirely of @ . . .
SAY . . . GET commands and related commands. Further, they
differ from ordinary programs in having the extension . FMT instead
of .PRG. These same commands could be used in an ordinary .PRG
program file, but putting them in an .FMT file gives you the conven¬
ience of using the program with the command SET FORMAT TO.
How can the format file be used without assigning some value to
each of its variables first? In fact, its variables do have a value
assigned to them: all its variables must be fields in the database file. If
you USE the file, SET the format, and then CHANGE, each variable
has the value of a field in the current record: this appears as the
default on the screen that you can either edit or press Enter to
confirm. If you USE the file, SET the format, and then APPEND, the
variables are all blank, as they have the values of the fields in the new,
blank record that you have added at the end of the file.
Like the format programs you generated with Fox View, @ . . .
SAY . . . GET commands can include RANGE and PICTURE
clauses to restrict the data that can be entered. These are simply
EXPANDING YOUR CAPABILITIES THROUGH PROGRAMMING 397
D Remember that, as
an abbreviation,
added at the end of the command. The word RANGE is followed by
two values (for maximum and minimum) separated by commas, as
you can use the first four
letters of a FoxPro com¬
you saw in the last chapter. The word PICTURE is followed by one
mand. You rarely see of the picture templates or picture functions, which you also learned
PICTURE in an actual about in the last chapter; all of the available symbols are listed in
program (unless the
Tables 10.1 and 10.2.
program is generated by
FoxView). It is almost
always PICT. Table 10.1: Picture Template Symbols
Symbol Effect
CH. 10
Symbol Effect
M < list > specifies preset choices, which are listed with commas
separating them (if the GET variable is not one of the
choices in the list when READ is executed, it is
replaced by the first choice on the list)
S < number > limits the width of the field displayed to the number
specified (used only with character data)
Symbol Effect
/V
displays numeric data using scientific (exponential)
notation (used only with numeric data)
* Program.: DATAENTR.FMT
* Author..: Charles Navasky Siegel
* Date....: 02/07/91
* Notice..: Copyright (c) 1991, SYBEX
* Version.: FoxBASE+, revision 2.10
* Notes...: Format file for EMPLIST.DBF
*
* EOF: DATAENTR.FMT
/■
CH. 10
This program has all the @ . . . SAY commands first, and then all
the corresponding @ . . . GET commands, so that it can use the
SET COLOR command to make the labels a different color from
the data-entry fields. It includes the PICTURE and RANGE clauses
that you entered in the FoxView table.
It also includes an interesting variation on the @ . . . SAY . . .
GET command: the line (about halfway down the list) that deter¬
mines how the box is to be drawn. This command includes the row
and column of the upper left corner of the box first, then the row and
column of the lower right corner of the box. (These values will proba¬
bly be a little different from your values, depending on precisely
where you placed your box in the exercise in Chapter 9.) Then, after
the word BOX, it lets you enter up to nine characters to specify the
type of lines used to draw the box. Remember that these line¬
drawing characters are extended ASCII characters, which you may
enter using the CHR() function rather than actually using the box
characters themselves, as FoxView does.
If you are doing the programming yourself for a data-entry screen
that is to have a box, there is an easier way of doing it than using this
command. Simply draw the box and labels using an editor that lets
you draw lines. When you are done, add the command @ <row >, 0
at the beginning of each line on your screen that has anything written
in it, either text or a box, and an additional quotation mark at the end
of each line. FoxPro will read the box-drawing characters and text on
each line as a character string, including any blanks in it, and will
draw the screen as your editor laid it out. You just need to add GET
clauses where you want the data-entry fields (and, if necessary, delete
enough blank spaces to make room for them).
One other useful member of this family of commands is @
<.row~>, Kcoiy CLEAR [TO <row>, <o>/>], which clears just part
of the screen: the area beyond the row and column that you specify at
the beginning. For example, @ 20,40 CLEAR will clear the screen
from the middle (column 40) to the end of line 20 and everything
below that. With the optional TO clause at the end, it will only clear
as far the second row and column that is specified.
For more information on this family of commands, see Appendix C.
EXPANDING YOUR CAPABILITIES THROUGH PROGRAMMING 401
CONTROL FLOW _
The simplest program is just a list of commands, executed from
beginning to end. The thing that really makes computer programs
powerful, though, is the ability to direct the flow of program control.
As you learned earlier in this chapter, the three types of control flow
used in structured programs are sequence, selection, and iteration
(or looping).
Sequence simply means that one command is executed after
another. This is the only form of control flow used in the sample pro¬
grams that you have tried so far. Now that you have learned about
input/output, you are ready to work with more sophisticated forms of
control flow.
LOOPING
The most important command used for iteration in FoxPro/
dBASE compatible languages is the DO WHILE loop, which has the
following form:
ENDDO
The ellipsis between the first and last line stands for any number of
lines of programming code.
Each time the program reaches this DO WHILE command, it
checks to see if the logical expression evaluates as true. If it is, the pro¬
gram executes the commands that follow. When it gets to ENDDO, it
loops back up to the DO WHILE and checks again to see if the logical
expression evaluates as true; if it is, it executes the same commands.
It will continue repeating this loop until the program discovers that
the logical expression does not evaluate as true, at which point it will
skip all these commands and instead execute the command that fol¬
On the rare occa¬ lows ENDDO.
sions where Esc Of course, the lines of code within the loop must do something that
does not work, remember
ultimately makes the condition untrue, otherwise the program will
that you can always get
out of an infinite loop by
continue executing this series of commands forever. This is a com¬
turning off the computer. mon error in programming, called an infinite loop. If your program
402 MASTERING FOXPRO
CH. 10
S FoxPro runs so
quickly that you
the Trace window, which is discussed in Chapter 12.)
Consider a simple example of looping, which makes your screen look
a bit like a primitive video game. Enter the listing in Figure 10.10
might not be able to see
every location of the > in a file named TEST4.PRG and run it: a bit of the output is shown in
symbol in TEST4.PRG Figure 10.11.
and TEST6.PRG: it
seems to jump across the
screen. You can see it in
every column in
TEST5.PRG, where you ************************************
*TEST4.PRG
add a delaying loop to *a sample program to demonstrate looping
slow its movement.
col_cntr = 0
DO WHILE col_cntr < 80
CLEAR
@ 10,col_cntr SAY ">"
col_cntr = col_cntr + 1
ENDDO
WAIT
Figure 10.11: Output of the sample looping program, showing the > character
after it has moved to column 79.
column 0 (since the value of 10,col_cntr is 10,0 this time through the
loop).
Then the program increments the value of col_cntr by one. The
line of code that does this, col cntr = col_cntr + 1, looks strange to
many beginning programmers. People are used to the meaning of
the = sign in arithmetic, where it signifies equality: in arithmetic,
of course, the equation col_cntr = col_cntr + 1 would be absurd,
since a number cannot equal one more than itself. In FoxPro,
though, as in most computer languages, the = sign represents assign¬
ment. This line of code should be read as ‘ 'make col_cntr equal to col-
_cntr plus one,” or as “let col_cntr equal col__cntr plus one.” Since
the value of col_cntr was 0 when the program got to this line, it makes
its value equal to 1.
When the program gets to ENDDO, it sends it back up to the top of
the loop, where it checks the condition following DO WHILE once
again. Since col_cntr is now equal to 1, the condition is still true, so
the program again executes the code in the loop. It clears the screen
and then prints the > sign at row 10, column 1, so that it looks as if
the sign has moved one column to the right. Then it makes the value
of col_cntr equal to 2, adding 1 to its current value of 1.
404 MASTERING FOXPRO
CH. 10
Thus, it continues going through the loop and printing the > sign
at column 2, column 3, and so on. When col_cntr is equal to 79,
though, it prints the > sign at row 10, column 79. Then it adds 1 to
col_cntr and makes its value 80. At this point, when it checks the con¬
dition of the DO WHILE loop, it finds that it is no longer true that col-
_cntr < 80 and so it does not execute the code in the loop again.
Instead, it continues with the next line of code after ENDDO.
This program illustrates the basic principle of a DO WHILE loop.
Some variable in the loop must change its value so that the condition
is ultimately untrue.
***********************************
*TEST5.PRG
*a sample program to demonstrate a delaying loop
***********************************
col_cntr = 0
DO WHILE col_cntr <80
CLEAR
@ 10,col_cntr SAY ">"
col_cntr = col_cntr + 1
tim_cntr = 0
DO WHILE tim_cntr < 100
tim_cntr = tim_cntr + 1
ENDDO
ENDDO
WAIT
Each time it goes through the main loop, the program makes
tim_cntr equal to zero; then it must add 1 to it 100 times before it can
continue. Notice how much more slowly it runs than it did before you
added this extra loop. This sort of time-killing loop can be useful at
the beginning of a program, if you want the program to display its
title screen for a time and then to begin automatically.
***********************************
*TEST6.PRG
*a sample program to demonstrate nested loops
***********************************
row_cntr = 0
DO WHILE row_cntr <25
col_cntr = 0
DO WHILE col_cntr < 80
CLEAR
@ row_cntr,col_cntr SAY ">"
col_cntr = col_cntr + 1
ENDDO
row_cntr = row_cntr + 1
ENDDO
The indented lines inside the main loop (the six lines beginning
with col_cntr = 0) are essentially the same as the earlier program,
TEST4.PRG. These lines display the > sign on each column across
the screen. The difference is that they do not just go across row 10, as
the earlier program did: instead, they are nested in a larger loop that
executes them on all the rows, one row after another. To begin with,
the row_cntr is 0. The program displays > at 0,0, at 0,1, at 0,2, and
so on until it has gone through all the columns and displayed it at
406 MASTERING FOXPRO
CH. 10
■A**********************************
*TEST7.PRG
*a sample program that loops through the records of a file
•k-k-k'k-k-k'k'k'k-k-k-k'k'k-k-k'k-k-k-k-k-k'k-k-k-k'k-k'k'klfk'k'kic
USE emplist
CLEAR
7
p
DO WHILE .NOT. EOF()
? PROPER(TRIM(fname)+" »+lname)
SKIP
ENDDO
7
WAIT
Audrey Levy
Jack Love
Edna Chang
Charlotte Sagorin
William Johnson
William B. Johnson
Nancy Nixon
James Skinner
Michelle Perlow
Joseph Cruz
Henrietta Johnson
SELECTION
Selection is the third method of control flow used in structured
programming.
FoxPro includes two basic methods of selection. When there are
just one or two choices, it is most convenient to use the IF . . . ELSE
. . . ENDIF command. When you have a larger number of choices,
it is most convenient to use the DO CASE . . . ENDCASE command.
408 MASTERING FOXPRO
CH. 10
IF .. . ELSE . . . ENDIF
The IF . . . ELSE . . . ENDIF command is fairly straightforward
and easy to understand. It takes the form
IF <logical exp>
ELSE
ENDIF
The ellipses represent any number of lines of code. If the logical expres¬
sion is true, the code following the IF clause is executed. If the ex¬
pression is not true, the code following the ELSE clause is executed.
This command can also be used without any else clause, in the form
IF <logical exp>
ENDIF
***********************************
*TEST8.PRG
*a sample of a DO loop nested in an IF statement
***********************************
USE emplist
CLEAR
7
Audrey Levy
Jack Love
Edna Chang
Charlotte Sagorin
William Johnson
William B. Johnson
Nancy Nixon
James Skinner
Michelle Perlow
Joseph Cruz
Henrietta Johnson
***********************************
*TEST9.PRG
*a sample of a DO loop combined with IF/ELSE
***********************************
USE emplist
CLEAR
•?
WAIT "Do you want the names capitalized (y/n) " TO yesno
•?
WAIT
CH. 10
AUDREY LEVY
JACK LOVE
EDNA CHANG
CHARLOTTE SAGORIN
WILLIAM JOHNSON
WILLIAM B. JOHNSON
NANCY NIXON
JAMES SKINNER
MICHELLE PERLOW
JOSEPH CRUZ
HENRIETTA JOHNSON
Audrey Levy
Jack Love
Edna Chang
Charlotte Sagorin
William Johnson
William B. Johnson
Nancy Nixon
James Skinner
Michelle Perlow
Joseph Cruz
Henrietta Johnson
Notice that this program could also be written with two separate
DO WHILE loops—one to print all the names capitalized and the
other to print them with normal capitalization, as shown in Fig¬
ure 10.20. The only difference is that the code is more compact in the
original form.
EXPANDING YOUR CAPABILITIES THROUGH PROGRAMMING 411
***********************************
*TEST10.PRG
*a less elegant method of combining a DO loop with IF/ELSE
***********************************
USE emplist
CLEAR
7
WAIT "Do you want the names capitalized (y/n) " TO yesno
7
IF UPPER(yesno) = "Y"
DO WHILE .NOT. EOF()
? UPPER(TRIM(fname)+" "+lname)
SKIP
ENDDO
ELSE
DO WHILE .NOT. EOF()
? PROPER(TRIM(fname)+" "+lname)
SKIP
ENDDO
ENDIF
7
WAIT
DO CASE . . . ENDCASE
The DO CASE . . . ENDCASE command is useful when there are
a larger number of choices.
It is possible to use the IF . . . ELSE . . . ENDIF command to select
among multiple choices, by nesting one IF . . . ELSE . . . ENDIF
within another. Consider the program shown in Figure 10.21, which
simply tells the user what number was entered. Figure 10.22 shows two
possible outputs of this program.
Look carefully at how this program works. All of the other IF . . .
ELSE commands are nested within the first ELSE. Thus, if the user
enters 1, the program executes the command under the first IF, then
it skips all the lines between the first ELSE and the last ENDIF. If the
user does not enter 1, though, the program executes the line under
the first ELSE, and it checks to see if the user entered 2. If the user
entered 2, it skips all the lines nested in the second ELSE, but if the
user did not enter 2, it executes the line under the second ELSE and
checks whether the user entered 3. Likewise, if the user did not enter
3, it checks to see if the user entered 4. Finally, if the user did not
enter 4, it prints an error message.
412 MASTERING FOXPRO
CH. 10
CH. 10
‘k-k-kick'k-k-kick’k’k'k'k-k-k-k-k'k-k'k-k'k-k-k-k-k'k'k-k'k'k-k-k-k
*TEST12.PRG
*a sample of DO CASE
***********************************
CLEAR
7
7
EXIT and LOOP are two commands that programmers use when
they want to make loop control explicit. EXIT breaks out of the loop
and directs control to the statement following ENDDO. LOOP
returns control to the DO WHILE statement. This makes it possible
to return to the beginning of the loop without executing some of the
commands that are in it.
It is often clearer to put an EXIT command within an infinite loop
rather than putting the condition after DO WHILE. You can create
an infinite loop by using a condition that is always true, for example,
DO WHILE 1 = 1. You can use a more elegant command, though, if
you remember that FoxPro evaluates any condition of this sort and
executes the loop if it evaluates as .T. To save it the trouble, you can
just use the condition DO WHILE .T.
Try rewriting the TEST12.PRG to add an infinite loop using the
EXIT and LOOP commands, as in Figure 10.24. Save this program
in a hie named TEST13.PRG and run it. Its output is shown in Fig¬
ure 10.25.
Notice that the command LOOP is not actually needed in this case:
the program would loop up when it reached the final ENDDO
EXPANDING YOUR CAPABILITIES THROUGH PROGRAMMING 415
***********************************
*TEST13.PRG
*a sample of EXIT and LOOP
***********************************
DO WHILE .T.
CLEAR
7
7
WAIT "Type a number between 1 and 4 > "TO usr_nmbr
7
DO CASE
CASE usr_nmbr = "1"
? "You typed one."
CASE usr_nmbr = "2"
? "You typed two."
CASE usr_nmbr = "3"
? "You typed three."
CASE usr_nmbr = "4"
? "You typed four."
OTHERWISE
? "Error: entry not between 1 and 4."
ENDCASE
7
WAIT "Do you want to try again? (y/n) " TO yesno
IF UPPER(yesno) = "Y"
LOOP
ELSE
EXIT
ENDIF
ENDDO
CH. 10
and the program would run in exactly the same way. In this case add¬
ing LOOP is merely a stylistic convenience, to make the program eas¬
ier to understand. In other cases, LOOP is used to bypass some of the
commands within a DO WHILE loop.
CH. 11
You will write the entire program in this chapter, but you will
write it in a fairly simple form. In the next chapter, you will modify
the program using some more advanced techniques. Even the basic
techniques used in this chapter, though, are enough to make you
capable of useful FoxPro programming. In fact, much of the work
that programmers do with dB ASE compatible languages is very simi¬
lar to what you will do in this chapter—setting up an application to
make it easy for the user. The programmer creates the database,
indexes, report, and label forms, and then writes a simple menu sys¬
tem to tie them all together.
FoxPro and other dBASE compatible languages are also used to
develop commercial programs. In these cases, programmers would
want to use pop-up menus and windows to create an impressive
interface, but these features are not really needed in the basic applica¬
tions that you would set up for most users.
The program you will write in this chapter, then, is a general-
purpose mailing list program that anyone can use, rather than an
application that is specific to a particular client, which (for example)
would support only that client’s label forms. The techniques you use
in this chapter are commonly used to program basic applications for
people who have acquired FoxPro or another dBASE compatible
program and who want to get down to their business without taking
the time to learn the program.
Finally, the program uses a stripped-down dialect of the Fox-
Pro/dBASE language, which you can use to write programs with
most dBASE compatible languages. You will see in the course of this
chapter how much easier the application is to use than FoxPro itself.
WRITE YOUR OWN PROFESSIONAL MENU APPLICATION 423
ANALYSIS _
Before you begin programming, you must analyze the problem you
are dealing with. Professional programmers who are computerizing a
business must go through a long process of analysis. Usually, they
begin by analyzing all the paper forms the business uses, and organiz¬
ing the data kept on all these forms into a single data “dictionary.”
Once they have the data listed in one place, they can see how it should
be normalized: generally, a problem this complex requires a relational
database. Before programming, they often use data flow diagrams to
show what department or what report uses each element of data. The
data flow suggests how their programs should be organized. In short,
programmers generally gather and analyze a tremendous amount of
information before they write even a line of code.
Of course, this mailing list application is simple enough that the
analysis can be relatively brief. Even with a simple application,
though, you should outline the program in writing before doing any
programming. An excellent way of doing this, which you will use in
this chapter, is the structure diagram. As you will see, this diagram
sketches out the basic functions that the program must perform and
thus gives you an idea of how the program should be broken down
into procedures.
First, though, you should consider the database file and indexes
that the program must use. We can call the file MAILLIST.DBF.
The fields that it needs are fairly obvious: in addition to name and
address, the program should also keep track of telephone numbers, to
make it a complete address book program. Thus, the fields that are
needed are
• first name
• last name
• company name
• address
• city
state
424 MASTERING FOXPRO
CH. 11
• zip
• telephone number
Even when the data is this simple, you should list it in writing as part
of your analysis. If you just start programming without analysis, it is
very easy to forget, for example, that you need an honorific in this
program. When you create the structure diagram and think about
exporting the data for mail-merge, however, you will be reminded
that your user may want to begin a letter with the salutation Dear
Mr. So-and-So, Dear Ms. So-and-So, or Dear Prof. So-and-So, and
that it is impossible to do this unless you have a separate held for title
or honorific.
As you can see, analysis is a dynamic process. Things that you do
in the later stages of analysis make you think about and maybe
change the things you have already done in earlier stages of analysis.
As I mentioned, it is best to put everything in writing in advance: it is
much easier to change written notes before you begin programming
than to change the code you have already written. It is very disturb¬
ing to suddenly realize, when you are in the middle of a project, that
you left a held out of your database, and that you have to redesign
your data-entry screens and reports and perhaps also rewrite many
procedures in your program.
Make key decisions during analysis. Should this program have a
held for notes? Should it have two lines for the address?—or should
you assume that the user can use the company name line for the hrst
line of a two-line address? The time to think about these things is
before you begin programming: make a decision that you can stick
with, because it becomes more and more difficult to change as the
project progresses.
One important question is how to handle deleted records. An
extreme solution would be to let the user recall deleted records until
they are packed, as you can with FoxPro itself. This is a bit confusing
for a simple program such as this one, though. At the other extreme,
you could SET DELETED ON so deleted records cannot be used,
and you could automatically PACK the records at some time (for
example, whenever the user exits from the program), then the user
would not even know about packing and would have the impression
that records were permanently deleted as soon as they made that
WRITE YOUR OWN PROFESSIONAL MENU APPLICATION 425
selection from the menu. This option has the disadvantage of wasting
time by packing unnecessarily, though: if you had a large database, it
could take a long time to quit the program.
Though there are arguments for both of the preceding options, this
program will take a middle course: it will SET DELETED ON, so that
the user will not be able to access deleted records, and will also pro¬
vide for a menu option to finalize deletions, so that there will not be
any time wasted. This feature would have to be explained to the user;
if this were an actual commercial program, it would be explained in
the documentation.
It should be fairly obvious to you what indexes you will need for
this program. Users will want to produce reports in alphabetical
order and to produce mailing labels in zip code order (if the program
is to be used for bulk mailing). Which of these indexes the pro¬
gram should generally use as the main index will become more clear
when you create the structure diagram.
• Data: lets the user add, edit, look up, or delete records
Since each of these presents the user with a menu, we can call them
DATAMENU.PRG, REPTMENU.PRG, LABLMENU.PRG
and EXPTMENU. PRG.
426 MASTERING FOXPRO
CH. 11
You can also see by looking at the structure diagram that this pro¬
gram is moderately complex. It would be difficult to start writing a
single program file that does all these things, as they used to do in the
days before structured programming. The structure diagram, though,
breaks it up into small pieces, each of which is easy to understand and
relatively easy to write the program for.
B An easy way to
create an attractive
module will do before you write it.
To begin with, it should display a title screen, with the program
title screen is to draw it
name and copyright. If you were writing a commercial program, you
with an editor that lets might use an editor that lets you use line-drawing characters to create
you use line characters. the title screen: making the letters out of the line characters can give
Then, when you have the
you an attractive title. Here, though, you can simply display the pro¬
title screen that you want,
just add an @ . . . SAY gram’s name and copyright using regular characters in the center of
statement at the beginning the screen.
of each line—begin¬
While the user is looking at the title screen, the program should
ning with @ 0,0—to
display the screen row by
USE the database file and index files, creating a slight delay before
row. Of course, you must the main menu appears; you can also use a delaying loop to make
use quotation marks to doubly sure the user has enough time to read the title screen. The
enclose what you have
drawn on each line,
program code that is listed makes the loop count up to 200, but if you
including any blank have a fast or a slow computer, you may want to use a higher or lower
spaces that are needed. number. At the same time, the program should SET environmental
variables: for example, you should SET TALK OFF, so that FoxPro
talk does not confuse the user.
430 MASTERING FOXPRO
CH. 11
Then, you can display the main menu with a heading at the
top; the four choices on the structure diagram, plus Quit; and a line
near the bottom asking the user to enter a choice. You will use a con¬
ventional menu program—a series of @ . . . SAY statements to dis¬
play the options and get the user’s choice, followed by a DO CASE
statement that makes the program perform some action that depends
on the choice that was entered. This menu program must be in a DO
WHILE loop, so that the menu screen is displayed repeatedly as long
as the user does not select Quit.
Under ordinary circumstances, you would probably use the Fox-
View screen generator to create the menu screen, so that you can
center the choices easily and use graphic characters to add boxes. As
an exercise, though, you will write this menu by hand, using a series
of @ . . . SAY commands: you should get experience with writing
these programs before you get in the habit of generating them, just as
you should learn to do arithmetic problems by hand before you start
using a calculator.
To make it easy for the user to enter choices, you use the first letter
of each choice as the entry. If you use an @ . . . SAY . . . GET state¬
ment to get the choice, and if you define the variable that the
statement “GETs” as just one character long, then the user can just
press a single key to make the choice, without pressing Enter after¬
wards. Because this keystroke fills up the field, FoxPro beeps and
goes on without waiting for the user to press Enter, just as it does
when you are doing data entry in a Browse window.
This makes it very convenient to move up and down a menu tree,
but the beeps are a distraction when you are using the menu. When
you are setting the environmental variables, then, you should also
SET BELL OFF. Then you can make the menu system beep only if
the user makes an error, by using the command ? CHR(7). Of
course, the beep is useful when you are doing data entry, so that you
know if you have filled a field; thus, you should SET BELL ON when
the user is modifying the data (but SET BELL OFF again after that
is done).
Finally, just before the user quits the program, you should return
all the environment variables to their default setting, using the com¬
mands SET TALK ON, SET BELL ON, and SET DELETED OFF. If
someone is using this program as an application within FoxPro,
rather than as a stand-alone application, they probably want the
WRITE YOUR OWN PROFESSIONAL MENU APPLICATION 431
CH. 11
Look carefully at how the main loop of this program works, since
you will see the same sort of thing very frequently in FoxPro and
other dBASE compatible programs. It is an infinite loop, with the
condition DO WHILE .T. at the top. The only way to get out of it is
by pressing Qto execute the command EXIT, which directs program
control to the line following the ENDDO.
If you press another key instead of Q, either the OTHERWISE
statement will beep or one of the CASE statements will execute a
related program, depending on whether your choice was invalid or
valid. Then, program control will be move to the next line after the
ENDCASE of this DO CASE statement. That line is ENDDO, the end
of the main loop, which directs control back to the beginning of this
DO WHILE loop and displays the menu once again.
You will avoid a couple of common errors when you write this sort
of program if you remember that the commands CLEAR and choice
= “ ” must be inside the main loop. The variable choice must be
made equal to a blank each time around, otherwise the value that it
was given the last time through the loop would be displayed by the
command GET choice, and the field where you enter your choice
would not be blank. Of course, the screen also must be cleared each
time the menu is displayed; otherwise the menu will just be superim¬
posed on whatever was on the screen previously.
WRITE YOUR OWN PROFESSIONAL MENU APPLICATION 433
Remember, also, to use GET with PICT “!” in this sort of menu
system, so the user can enter the letters in upper or lower case.
This menu could use a loop with the condition DO WHILE choice
< > “Q” instead of the infinite DO WHILE .T. loop. If you do this,
you would have to initialize the value of choice twice—once before the
loop begins, so the condition is true the first time the program comes
to the DO WHILE statement, and once within the loop, so choice is
made a blank each time around. DO WHILE .T. saves you a tiny bit
of typing. What is much more important, though, is that most people
find that the DO WHILE .T. loop makes the program easier to fol¬
low. You can easily see what happens when the user selects Q,
because it is right there next to the other selections in the DO CASE
statement. There is no need to search for the beginning of the loop to
find what choice lets the user get out of it—and this can be a signi¬
ficant advantage if you are trying to understand a long program.
It is also possible to use the commands following ENDDO within
the DO CASE statement, following CASE choice = “Q”. The pro¬
gram uses the command EXIT if the user selects Q,, in order to break
out of the loop and get to the commands that follow ENDDO. But
why not save a line of code by putting those commands right in the
DO CASE, where EXIT is now? The reason is, studies of structured
programming have found that programs are easier to understand if
control terminates at the end of each module. Though there may be
cases where it is best to put RETURN or QUIT somewhere in the
middle of a module, it does make the program harder to understand
and maintain.
You can see the advantage in this example. To begin with, the pro¬
gram has an asterisk before QUIT, to make it a comment. When you
are testing and debugging the program, you do not want to quit Fox¬
Pro and return to DOS each time you finish running it, because you
need to use FoxPro to modify and retest it. When you are done with
testing, though, you could delete the asterisk so QUIT is executed and
the program returns the user to the operating system when it is done,
rather than returning to FoxPro. Thus, you could make the program
act as a stand-alone program rather than just an application within
FoxPro. It obviously will be easier to make this change because QUIT
is on the last line. Likewise, if you add any other environment settings
in the course of developing the program, it is very easy to set them off
by adding the commands at the end of the program.
434 MASTERING FOXPRO
CH. 11
STUB TESTING _
Structure: C:\MAILP0W2\MAILLIST.DBF
Name Type Width Dec
Field
* HONORIFIC Character 5
t FNAME Character 15 <Insert>
t LNAME Character 20
t COMPANY Character 50 <Delete>
t ADDRESS Character 50
t CITY Character 20
t STATE Character 2
t ZIP Character 5 ■ < OK - ■
t PHONE Character 13
<Cancel>
CH. 11
***********************************
★DATAMENU.PRG
*stub for testing
★called by MAINMENU.PRG
***********************************
CLEAR
WAIT
***********************************
★REPTMENU•PRG
★stub for testing
★called by MAINMENU.PRG
***********************************
CLEAR
WAIT
***********************************
★LABLMENU.PRG
★stub for testing
★called by MAINMENU.PRG
***********************************
CLEAR
WAIT
***********************************
★EXPTMENU.PRG
★stub for testing
★called by MAINMENU.PRG
***********************************
CLEAR
WAIT
D - Data
R - Reports
L - Labels
Q - Quit MAILPOWER!
Keep testing the program until you are sure this module runs cor¬
rectly. Since you are testing just one module, and its logic is quite
straightforward, it should be easy for you to correct any bugs.
When you look at your structure chart, you will notice that you
need to create and test the Data submenu next. After all, you cannot
actually test the Report, Label, or Export modules until you have
used this one to add data to the file.
This module itself calls two other modules, a screen format (which
it uses for appending and editing data) and a LOOKUP program
(which it uses for looking up, editing, and deleting records—when
the user must ask for a specific record—but not for appending data).
Obviously, you must have some data before you can edit or delete
any. For the purposes of testing, then, you can begin by writing the
.FMT program that lets you enter data, and writing just a stub of
the LOOKUP program. This allows you to test the Data submenu
itself and to use it to add data. Then, after you have added data, you
will write and test the actual LOOKUP program.
438 MASTERING FOXPRO
CH. 11
You might find it 1. Enter RUN DEL DATAMENU.PRG to delete the stub you
easiest to create this created earlier.
program by editing the
file MAINMENU.PRG 2. Create a new program file and enter the code for the Data
and then saving it with submenu in it, as it is listed in Figure 11.7. The menu screen
the changes that you have
is shown in Figure 11.8. As you can see, this menu is very
made, under the name
DATAMENU.PRG. Be similar to the menu that you created previously.
sure to select Save As
from the File menu when
you are done: if you select
**************************************************
Save, you will overwrite
*DATAMENU.PRG
the previous program. *The Data submenu for Mail Power
♦called by MAINMENU.PRG
**************************************************
*-create the main loop, to repeat the menu indefinitely
DO WHILE .T.
ENDDO
RETURN
CH. 11
can add data using this custom screen. When the user is done
appending and presses Ctrl-End or Ctrl-Q, control returns to the
program. Then, the command SET BELL OFF stops the program
from beeping when you make your next menu selection. The com¬
mand SET FORMAT TO closes the format file, so the DATASCRN
format does not interfere with any of the program’s later commands:
an active format file can cause trouble whenever you do formatted
input/output, so it is always best to close it as soon as you are done
with it.
Other options in this menu assume that you have a LOOKUP
program, which lets the user enter the name being searched for, uses
a SEEK command to find it in the database, and displays the names it
has found until it has either displayed the right one or run out of
matching names; if the record is not found, the LOOKUP program
makes sure that EOF() has the value of .T.
If the user selects Edit, the program uses LOOKUP to find the re¬
cord that should be edited. If it finds it, the pointer is on that record,
so this program can use the commands SET BELL ON and SET
FORMAT TO datascrn as well as EDIT to edit the current record—
much as the previous option used SET BELL ON and SET FORMAT
WRITE YOUR OWN PROFESSIONA L MENU APPLICATION 441
CH. 11
**************************************************
* DATASCRN.FMT
* format for appending, editing, and displaying data
* called by DATAMENU.PRG
**************************************************
@ 0,0 SAY "MAILPOWER!"
@ 0,70 SAY DATE()
@ 1,0 SAY "_
Figure 11.9: The format program for editing, appending, or deleting records.
Figure 11.10: The data-entry screen produced by the program in Figure 11.9.
444 MASTERING FOXPRO
CH. 11
it does not find it, will print an error message and make EOF() true,
so that DATAMENU will not actually try to edit or delete the non¬
existent record.
For the purposes of testing, we can use a stub of LOOKUP that
never finds the record it is looking for. With this stub, we can test
DATAMENU.PRO and use it to append records but not to delete or
edit records. After you have appended some sample records, you can
rewrite LOOKUP in its final form, and then you can test it by
searching for some of the records you added earlier and try deleting
or editing them. The program in Figure 11.11 will never find the
record it is looking for because the screen format program makes sure
that all entries are made in capital letters, and this stub seeks a lower¬
case letter.
'k-k-k-k-kick'k-k-k-kitick’k-k'k-k'k-k-k-k-k-k-klc-k-k'k'k-k-k-k’k'k-k-k-k'k'k'k-k-k-k'k'k-k-k-k'k
*LOOKUP.PRG
*stub for testing
*called by DATAMENU.PRG
■k'k-k-k-k'k’k-k-k'k'k-k-k-k-k-k-k-k-k'k’k'klck-kic'k-k'kif-k'k'k'k-k-k'k'kifk-k'kick-k-k-k-k-k-k
CLEAR
SEEK "a"
? "Record not found."
WAIT
PRELIMINAR Y TESTING
Now you can test some features of the DATAMENU program.
Make all the selections from the Data menu. Try editing, deleting, and
looking up a record, even though you know that the program will not
find the name you are looking for. Use the menu to add five or six
records. Try adding them using lowercase letters, to make sure all the
fields are capitalized. Try adding letters in the Zip and Phone fields. Be
sure to include at least three records that have the same last name, so
you can use them to test the LOOKUP program, which you add next.
WRITE YOUR OWN PROFESSIONAL MENU APPLICATION 445
CH. 11
**************************************************
* LOOKUP.PRG
* lookup a record for editing, deleting or displaying data
* called by DATAMENU.PRG
★*************************************************
* -create a variable to hold the name the user wants
mlookfor = SPACE(20)
@ 8,8 SAY "Enter the last name of the record you want:";
GET mlookfor PICT "@1"
@ 11,12 SAY "(Enter the entire last name or just the
+"initial letters)"
@ 13,20 SAY "(or press Enter to return to the menu)"
READ
* -trim blanks, in case the user did not enter whole name
* -or entered leading blanks by mistake
mlookfor = ALLTRIM(mlookfor)
EXIT
DATASCRN.FMT ENDIF
ENDIF
in order to create
ENDD0
LOOKUP.PRG. When ENDIF
LOOKUP asks the user
if the record it has found
is correct, this program Figure 11.12: The module for looking up names, (continued)
displays the data in a
form that is similar
lines tell the user to enter all or just the beginning of the name (since
to the one used by
DATASCRN.FMT. you have not SET EXACT ON, FoxPro can find a match with only
This gives the program a some of the letters) and to press Enter to return to the menu (and can¬
consistent feel and looks
cel the command). It is generally a good idea to give users the chance
good when the program
moves from looking up to to cancel a command of this sort, as you no doubt realize if you ever
editing a record. used a program that does not let you cancel.
If the user simply presses Enter, so that the variable that holds the
name is still equal to 20 blanks, the program moves the pointer to
make EOFQ true and then returns to the DATAMENU.PRG; since
EOFQ is true, DATAMENU will not try to delete or edit the current
record. Using RETURN in the middle of a module in this way is not a
perfect example of structured programming, but it is justified,
because it would be so much more trouble to nest the entire module
in a DO WHILE loop just to be able to use EXIT.
If the user does enter a name, this program goes on to trim blanks
from it in case the user entered leading or trailing blanks by mistake;
thus it will just search for the letters entered. Then it seeks that name.
448 MASTERING FOXPRO
CH. 11
MAILPOWER! 03/15/91
Telephone: (415)284-1059
Figure 11.14: The program displays the name and asks if it matches.
nothing else needs to be done, and DATAENTER just asks the user
to press the key to continue. If the user wants to edit or delete, the
pointer is on the right record, and the calling program can do what is
needed.
If the user does want to continue the search for another record with
the same name, the LOOKUP skips to the next record and checks it to
see if it matches. If it does match, the command LOOP sends the pro¬
gram back to DO WHILE .T. so that it displays the data in the new
record and asks the user if it is the right one. The program keeps doing
this until it finds a record that does not match.
When it finds a different name after exhausting all the matching
names in the file, it displays a message saying that a matching record
is not in the file. Then it uses GO BOTT and SKIP to make EOF()
equal to .T., and it exits from the DO WHILE loop so that it returns
to the calling program. As usual, because EOF() equals .T., DATA-
MENU does not try to edit or delete a record.
To sum up, then, if a match was found, the pointer is on the
matching record, so that DATAENTR can do what is needed. If no
match is found, EOF() is true, so that DATAENTR does not do
something foolish.
450 MASTERING FOXPRO
CH. 11
MAILPOWER! 03/15/91
Telephone: (415)284-1059
4" x 2V4" Rolodex cards, you can also give the user these options on
the Report menu.
When you save these forms, there is no need to save the environ¬
ment. The program itself makes sure that the proper database file
and index is in use when the report or labels are produced, so the
REPORT FORM and LABEL FORM commands that the program
uses to produce them will not have to include the ENVIRONMENT
option that makes them use these saved environments.
1. You must create the first two reports by using the report lay¬
out window. The database file should already be in use from
the program testing; if it is not, enter USE MAILLIST. Select
New from the File menu. Select the Report radio button, and
select OK.
2. Select Page Layout from the Report menu. Make the top
margin 6, the bottom margin 6, the printer indent 5, and the
right margin column 75. Then select OK.
3. Move the cursor to the second line of the page header band.
Type MAILPOWER! Complete Report. Press Enter to stop
editing the text and the space bar to select the text object.
Select Center from the Report menu to center it, and press
Enter to deselect it.
4. Move the cursor to the second line of the detail band. Select
Add Line from the Report menu to add a line to the detail
band.
CH. 11
6. Move the cursor down a line, then move it to the left margin.
Press the right arrow key five times. Select Field from the
Report menu, and, in the text box, enter the expression
PROPER(FNAME) and place it as in Step 5.
7. Move the cursor down a line and to the left margin. Place the
field expression PHONE, as in Step 5.
8. Move the cursor up one line and right to column 21. Use the
menu to place the expression PROPER(COMPANY) as
above.
11. Move the cursor to the footer band. Select Remove Line
from the Report menu to remove one line. Move the cursor
to the second line of the three in the page footer band and to
the left margin.
12. Now, since the report may be long, you should add page
numbers. Select Expression from the Report menu, then
select the Expression text button to call up the expression
builder. In the text box, type “Page Number ” (do not forget
the quotation marks). Select the String popup control and
select + , select the String popup control again and select
LTRIM(), then select the String popup control once more
and select STR(). From the scrollable list of memory vari¬
ables, select _PAGENO. If you want, select the Verify text
button to make sure the expression is valid. The expression
should look like Figure 11.16. Select the OK text button to
return to the Report Expression dialog box, and select the
OK text button to place the expression. Press the space bar to
select the expression and then select Center from the Report
menu to center it. Press Enter to deselect it.
WRITE YOUR OWN PROFESSIONAL MENU APPLICATION 453
13. You now have the complete report form shown in Figure
11.17. Select Save As from the File menu and, when the Save
Report As dialog box appears, type the name COMPLETE,
select the Environment check box so that it is not checked,
and then select the Save text button to save the file.
14. Now, to create the second report, alter this form so it pro¬
duces a report with just names and telephone numbers.
Remove the second and third line in the detail band by put¬
ting the cursor on them, selecting Remove Line from the
Report menu, and entering Y to confirm that you want to
remove the objects on the lines. Move the cursor to PRO-
PER(COMPANY) and then select and delete this expres¬
sion. With the cursor on column 22, place the expression
PROPER(FNAME). With the cursor on column 40, place
the expression PHONE. Move the cursor to the tide, select
Text from the Report menu so you can edit the title, and
change it to MAILPOWER! Phone Report. When you are
done editing, select this text object and select Center from the
Report menu to center it. Then deselect it.
454 MASTERING FOXPRO
CH. 11
15. Select Save As from the File menu. When the Save Report
As dialog box appears, type PHONES in the text box, make
sure the Environment check box is not checked, and select
Save to save the report under this name. The final form of
this report is shown in Figure 11.18. Then close the report
layout window.
Char exp represents the character expression that you want to use a
substring of. Num expl is a numeric expression that you use to specify
which character you want the substring to begin with. Num exp2 is an
optional numeric expression that you use to specify the length of the
substring; if this expression is omitted, the substring continues until
the end of the string.
For example, the function
SUBSTR(/,abcdefghijkl,,,1,3)
would return the value abc. This substring starts with the first charac¬
ter of the string specified and is three characters long. To give
another example, the function
SUBSTRC'abcdefghijkrjO)
would return the value jkl, since this substring starts with the tenth
character of the string specified and continues to the end.
In the exercises below, you will use this function to make a field fit
in the width of the label form. For example, if the label form is 40
456 MASTERING FOXPRO
CH. 11
SUBSTR(PROPER(ADDRESS),1,40)
to enter its address. This function returns a substring that begins with
the first character of PROPER(ADDRESS) and includes 40 charac¬
ters. If the address field is more than 40 characters wide, this function
will simply cut off its final characters, so it fits in the label form.
1. To create the next “report,” select New from the File menu.
Select the Fabel radio button, and select OK. When the label
layout screen appears, select Layout from the Label menu
and select 3" x 5" Rolodex. Then fill out the label layout
screen as illustrated in Figure 11.19. Select Save As from the
File menu, select the Environment check box so it is not
checked, and save the label form, using the name INDEX.
2. To create the next “report,” select 4" x 2V4" Rolodex from the
Label menu. The new label layout will keep the fields that were
there, and you can edit them so they they look like the form
shown in Figure 11.20. Then select Save As from the File
menu, make sure the Environment check box is not checked,
and save the label form using the name ROLODEX.
WRITE YOUR OWN PROFESSIONAL MENU APPLICATION 45 7
1
t
4- Lines Between
1
CH. 11
*REPTMENU.PRG
*The report submenu for Mail Power
*called by MAINMENU.PRG
**************************************************
*-create the main loop, to repeat the menu indefinitely
DO WHILE .T.
ENDDO
RETURN
C - Complete Report
CH. 11
2. Select Layout from the Label menu and select the first standard
format on the list, V/2" x 15/i6" x 1. The fields all remain on
this new form. Since the width of this column is 35, change the
name line to
SUBSTR(ADDRESS,1,35)
3. Select Save As from the File menu and save this under the
name ONE-COL (since it produces one-column labels).
Make sure not to save the environment.
Notice that the name line was altered so that the first name is trun¬
cated if the name is too long to fit in the label: at most, the name can
consist of 14 characters from the first name, one blank, and twenty
characters from the last name, for a total of 35 characters.
Now, you should continue to produce labels with all the other
default layouts on the label menu. Produce them as you did above,
by selecting the layouts listed below, editing the character expressions
where needed, and selecting Save As from the File menu to rename
them. (The first few will not need editing, as they just use same-size
labels in a two-column and three-column format.)
Use the following names and field expressions:
Name TWO-COL
SUBSTR(COMPANY, 1,35)
TRIM(CITY) + “ ” + STATE + “, ” +
ZIP
Name THRE-COL
SUBSTR(COMPANY, 1,35)
TRIM(CITY) + “ ” + STATE + “, ” +
ZIP
Name LARGE
SUBSTR(COMPANY, 1,32)
TRIM(CITY) + “ ” + STATE + “, ” +
ZIP
Name CHESHIRE
SUBSTR(COMPANY, 1,40)
TRIM(GITY) + “ ” + STATE + “, ” +
ZIP
Name SMALLENV
Fields
462 MASTERING FOXPRO
CH. 11
SPACE(15) + TRIM(FNAME) + “ ” +
TRIM(LNAME)
SPACE(15) + COMPANY;
SPACE(15) + ADDRESS
Name LARGEENV
Fields
SPACE(25) + TRIM(FNAME) + “ ” +
TRIM(LNAME)
SPACE(25) + COMPANY;
SPACE(25) + ADDRESS
Once you are done creating all the label forms, write the Label menu
program to tie them together, using the code shown in Figure 11.23,
which will display the menu screen shown in Figure 11.24. Test all the
new options you just added.
WRITE YO UR OWN PROFESSIONAL MENU APPLICATION 463
ic-k'k-k-k-k-k'k'k'k-kick-k-k-k-k-k-k-k-k-k'k-k-k'k-k'k-k'k-k'k'k-k-k'k'k'k-k-kick-k-k-k'k-k-k-k-k
*LABLMENU.PRG
♦The label submenu for Mail Power
♦called by MAINMENU.PRG
**************************************************
*-create the main loop, to repeat the menu indefinitely
DO WHILE .T.
ENDDO
RETURN
CH. 11
1 - One-column labels
2 - Two-column labels
3 - Three-column labels
C - Cheshire labels
S - Small Envelopes
W - Wide Envelopes
**************************************************
*EXPTMENU.PRG
*The export submenu for Mail Power
★called by MAINMENU.PRG
**************************************************
*-create the main loop, to repeat the menu indefinitely
DO WHILE .T.
ENDDO
RETURN
CH. 11
While you are testing the program, you might want to review
some of the code to make sure you understand it. If you understand
the programming techniques used in this chapter, you can begin set¬
ting up applications for users. Though there are more advanced pro¬
gramming techniques for you to learn, the programs in this chapter
represent the bread and butter of database programming.
>
Using Advanced
Programming Techniques
To combine the modules of a program in a single file, 473
use the command PROCEDURE Kprocedure name^> followed
by the code in a module.
To pass values back and forth between two program modules, 478
it is best to use a user-defined function. You can begin this with
the command FUNCTION Kfunction name> or PROCE¬
DURE <procedure name>. These commands are identical.
To pass values to a user-defined function, 480
put the value in the parentheses of the function, just as you do
when you are using a built-in FoxPro function. The user
defined function must begin with the command PARAM¬
ETER Kmemvar list>, and the expressions you put in the
parentheses when you call it are assigned to the memory vari¬
ables in order.
CH. 12
ADVANCED TECHNIQUES OF
STRUCTURED PROGRAMMING -
You have seen that structured programming involves breaking the
program down into smaller parts. In most structured programming lan¬
guages, all of these modules can be kept in a single file, and each one is
called a subroutine or a procedure. It is generally easier to keep track of
what you are doing when the entire program is there in one file.
DBASE II did not let you create several procedures within a single
file. Each module of the program had to be in a separate .PRG file, as
they were in the Mail Power! program that you created in the last
chapter. This is adequate for simple programs, but as developers
began to use dBASE to create more complex applications, they
started complaining about this limitation.
As a result, dBASE III let users create procedure files, which could
hold many procedures. This innovation let programs run more
quickly, and it made programming somewhat easier, since modules
of the program did not all have to be in different files, but it was still
necessary to put procedures in a separate file from the main .PRG
file, which is executed when the program is started.
FoxPro goes a step further and lets you put procedures in the main
program file itself, so that you can now write programs as you do in
almost every structured language.
It is common for programmers to accumulate libraries of proce¬
dures that they have found useful for many purposes. These can be
kept in separate procedure files, so they can be used by any program
that you write. It is also common for programmers to keep all the new
procedures written for the current program in a single file, and now
FoxPro lets you do this as well.
CH. 12
Remember this If the procedure is in a separate procedure file, you must use the
default order of command SET PROCEDURE TO <file name> before doing it. If
searching to avoid confu¬
the procedure is in the same file as the program that is doing it, you
sion. In case you create
more than one program do not need to use the SET PROCEDURE command. When it sees a
or procedure with the DO < name> command, FoxPro looks first in the current file to see if
same name, FoxPro
there is a procedure with the specified name. Then, it looks in a pro¬
might not execute the
one you expected. cedure file, if one has been opened previously using SET PROCE¬
DURE TO, for a procedure with the specified name. Then, it looks
for a .PRG file with the specified name.
Like a .PRG file, a procedure can use the command RETURN at
any point to return to the program or procedure that called it. It can
optionally include this command at the end, but FoxPro automati¬
cally returns to the calling program when it reaches the end of the
procedure, just as it does when it reaches the end of a program.
In fact, procedures are so similar to programs that you can per¬
form a simple exercise to get experience with the PROCEDURE com¬
mand by combining all the .PRG files in your Mail Power! program
into a single .PRG file.
The code that is now in MAINMENU.PRG will be at the beginning
of this new .PRG file, so that the Main menu is executed when the pro¬
gram begins. All of the other .PRG files you created in the last chapter
will be procedures within the same file: all you have to do is use your edi¬
tor to copy them into the file and then add the command PROCEDURE
plus the name of the .PRG file at the beginning of each one. When Fox¬
Pro sees a command such as DO DATAMENU, it will do the datamenu
procedure rather than the datamenu program.
FoxPro includes a utility named FoxBind that turns separate
.PRG files into procedures for you, which you might want to learn
later. For a fairly short program such as this one, though, it is very
easy to do the same thing by hand. You should do it yourself for now,
so that you learn the PROCEDURE command.
When you created the original .PRG files, the FoxPro editor auto¬
matically put a DOS end-of-file mark at the end of each one. This
mark shows up in the FoxPro editor and in most editors as a small
arrow pointing right. In some editors, though, it shows up as ~Z
(Gtrl-Z represented by a caret followed by Z). To avoid possible con¬
fusion, you will delete this character. If you have changed editor pref¬
erences, however, it might cause even more confusion: make sure the
Gtrl-Z Sensitive check box is not checked.
USING AD VANCED PROGRAMMING TECHNIQUES 475
3. Press Enter five or six times, to skip lines before the next pro¬
cedure. Then type PROCEDURE datamenu, and press Enter
twice to skip more lines. Then select Open from the File
menu. Use the popup control of the Open dialog box to select
Program. Select DATAMENU.PRG and press Enter or
select the Open text button to edit that file. Press Shift-Ctrl-
End to mark all the text in the DATAMENU.PRG file.
Select Copy from the Edit menu to copy all the text in the
file. Then press Esc or click the close box to close it and to
return to the end of the MAINMENU. PRG file, a couple of
lines below the command PROCEDURE datamenu, which
you entered a moment ago. Select Paste from the Edit menu
to place the DATAMENU.PRG file that you copied in this
location. The cursor should be at the end of the file you just
pasted: press Backspace to delete the arrow that is the end-of-
file marker, as you did before.
5. Since this the entire Mail Power! program, you will save it all
under the name MAILPOW.PRG. First, scroll up through it
and modify the comments at the beginning of each procedure
to reflect the changes you made. Though the program will
run perfectly well in its current form, the comments you
wrote when the procedures were separate programs are no
longer quite accurate. Instead of DATAMENU.PRG, for
example, the comment should say DATAMENU PROCE¬
DURE; and you will probably also want to move the com¬
ments so they come above the PROCEDURE command.
There is no longer a separate MAINMENU.PRG to call
these procedures, but it is conventional in many program¬
ming languages to refer to the module of the program that is
executed when it begins as the main module, and you might
want to change your comments using this terminology. You
might want to look ahead to the final version of the program
file (shown in Figure 12.15) to copy some of its comments.
6. Once you are satisfied with the comments, save the file by
selecting Save As from the Program menu. Enter the name
MAILPOW in the Save Current Document As dialog box, and
select the Save text button. Then close the editing window.
□
AND PASSING PARAMETERS
You define the In addition to introducing procedures, dBASE III also added fea¬
scope of a memory tures that give you more control over memory variables in your pro¬
variable in the same way,
regardless of whether the
grams. Though it was not necessary to the programming you did in
modules of your program the last chapter, when you do more complex programming you often
are in procedures or in want to control whether memory variables are accessible to all the
separate .PRG files.
modules of the program or only to the module where they are cre¬
ated. This is sometimes called the scope of the variable.
To determine a variable’s scope, you can use one of two simple
commands at the beginning of any .PRG file or procedure:
CH. 12
/) /W&t/c tPY/Sts* FV^-aJ ~n¥£r fAo&Ztf/ff
-/YYA T T£P YT .
CLEAR
@ 0,0 SAY "MAILPOWER! Data Submenu"
@ 0,70 SAY DATE()
@ 1,0 SAY "_
+"
Figure 12.1: The original code to create the Data submenu header.
******************************************
*PROCEDURE SCRNHEAD
*a general purpose screen header
*called by the MAIN program and by
*procedures DATAMENU, REPTMENU, LABLMENU, EXPTMENU, LOOKUP
*******************************************
PROCEDURE scrnhead
PARAMETER menuname
CLEAR
@ 0,0 SAY "MAILPOWER! " + menuname
@ 0,70 SAY DATE()
@ 1,0 SAY "_" ;
+ ii ii
✓✓ //
DO scrnhead WITH
480 MASTERING FOXPRO
CH. 12
USER-DEFINED FUNCTIONS
It is also possible to use the PARAMETER command to pass a
value back to the calling procedure. Although this was common in
dBASE III + programming, it is no longer necessary in FoxPro,
because there is a much more elegant way of accomplishing the same
thing, using user-defined functions.
You are no longer limited to the functions that are provided as part
of the FoxPro language. If they are inadequate for your purposes,
you can create functions of your own, which you can use just like the
program’s built-in functions.
FoxPro lets you use the command FUNCTION just as you use the
^command PROCEDURE. In fact, the way that these two commands
work is identical, but as a matter of programming style it makes sense to
use FUNCTION at the beginning of a user-defined function and PRO¬
CEDURE at the beginning of a procedure, in order to make the pro¬
gram easier to understand when you are modifying or debugging it.
USING AD VANCED PROGRAMMING TECHNIQUES 481
CH. 12
you have finished, select Save from the File menu and then
close the window.
Command
MODI COMM MYFUNCTS
SET PROCEDURE TO MYFUNCT
?
? INITCAP("KNOW THYSELF!
As you can see, you use the INITCAP0 function that you created
yourself in the same way that you use built-in functions such as
UPPER() and PROPER0. The parameter that you pass to the func¬
tion is placed in the parentheses of the function, and the expression
that it returns is the value of that function. User-defined functions,
like any functions, can be used either in programs or from the Com¬
mand window.
Though you can manage without it when you are doing basic
database programming, you will find that passing values between
modules in this way becomes more and more important as you
become a more advanced programmer. In the rest of this chapter,
you will look at more sophisticated examples of parameters and user-
defined functions.
CH. 12
mfname = BLANK(15)
mlname = BLANK(20)
and so on, creating a memory variable for each field in the database,
with the same length as the field and a similar name (with the initial
m added to show that it is a memory variable).
Then you use a series of commands such as
and so on for all the fields of the database file, and then the command
READ to have the user enter data. The user is able to access only the
memory variables, not the actual database.
Finally, when the user has entered all the data (and, if you choose,
has confirmed that it is correct), you use a series of commands such as
APPEND BLANK
REPLACE fname WITH mfname
REPLACE Iname WITH mlname
USING AD VANCED PROGRAMMING TECHNIQUES 485
and so on for all the fields in the file. You add the new record by using
the command APPEND BLANK rather than APPEND, so that the
user still does not have access to the database file. Then you replace
all the fields in this new blank record with the data that the user
entered.
If you want to edit an existing record rather than appending a new
one, you use a very similar technique. The difference is that you first
must look up the record that the user wants to edit, and initialize all
the memory variables with the current values of its fields. If your pro¬
gram has a LOOKUP module that works like the one you wrote in
the last chapter, for example, you could write
DO lookup
IF .NOT. EOFO
mfname = fname
mlname = Iname
and so on, giving all the memory variables the values that the fields
currently have (assuming the program found the record that the user
wants to edit).
Then, to let the user modify them, you could use much the same
code you used for appending. The commands
and so on would display default values in the GET field that are the
same as the values in the current record. Then when the command
READ is executed, the user could change these defaults or keep them.
H Though it is easier to
understand for
Finally, when the user is done, the commands
CH. 12
when you use EDIT or CHANGE. In this way the programmer can
keep a close watch over the integrity of the data.
Despite the similarity between them, database programmers
sometimes write two separate modules for appending and editing:
they must write the code twice for initializing the memory variables,
displaying them on the screen, getting user input, and replacing the
actual variables with memory variables. That is the quick-and-dirty
way to do things, but it could end up being more work in the long
run: for example, if you want to modify the screen display, you must
rewrite all the @ . . . SAY . . . GET statements twice and look back
and forth between the two versions to make sure they are identical.
Since this chapter is about more structured methods of program¬
ming, we will do the extra thinking that is needed to write a module
called GETDATA, which will let the user both edit and append data.
Because there are slight variations in the things that GETDATA
must do to append and to edit, the DATAMENU procedure will
pass a different parameter to it depending on what must be done, and
it will include IF statements that make it execute code depending on
the parameter. This is a somewhat more sophisticated use of param¬
eters than in the earlier exercise, where the parameter was just dis¬
played as part of the header.
Remember the original bit of code from the DATAENTR proce¬
dure, shown in Figure 12.5, that was used to append and edit. To
revise this procedure so that is can be used with the new GETDATA
procedure, you will replace it with the code in Figure 12.6.
You can begin to see already that this is a more elegant way of writ¬
ing the program. For example, notice that SET BELL ON and SET
BELL OFF have been removed from both of these: it is obvious that
GETDATA can use them once for both editing and appending.
(LOOKUP will also be included in GETDATA, for a reason that
will become apparent when we write that module.)
GETDATA will display a screen similar to the screen that the orig¬
inal format file displayed to get input from the user. But first, GET¬
DATA must use DO LOOKUP if it is editing data; then, if
LOOKUP finds the record it wants, it will go on with code that ini¬
tializes memory variables with the values in the fields of the current
record of the database file.
USING AD VANCED PROGRAMMING TECHNIQUES 487
********************************
DO CASE
CASE choice = "A"
* -append using custom format screen
SET BELL ON
SET FORMAT TO datascrn
APPEND
SET BELL OFF
SET FORMAT TO
CASE choice = "E"
* -find record user wants and edit
* -using custom format screen if found
DO LOOKUP
IF .NOT. EOF()
SET BELL ON
SET FORMAT TO datascrn
EDIT
SET BELL OFF
SET FORMAT TO
ENDIF
ENDCASE
Figure 12.5: Code for appending and editing from the first version of the
program.
********************************
♦program fragments revised code for appending and editing
♦to be incorporated in PROCEDURE DATAMENU
*******************************
DO CASE
CASE choice = "A"
*-append using GETDATA
DO getdata WITH "append"
ENDCASE
CH. 12
Thus, when it initializes all the memory variables with the values in
the fields of the current record, it will give them the values in the record
to be edited if it is editing, and it will simply give them the values in the
new blank record if it is appending.
In either case, after initializing the memory variables, it displays
them with a series of @ . . . SAY . . . GET statements and lets the
user change them. If the user confirms that the changes should be
kept, it uses a series of REPLACE statements to enter them in the
database file.
If the user does not want to keep them, the program does not have
to do anything if it is editing: it just omits the REPLACE commands
and leaves the original data there in the record. If it is appending,
though, it must do something with the blank record it appended at
the beginning of this procedure. The simplest thing to do is just
to DELETE this blank record on the spot: since this program has SET
DELETE ON, the blank record that is marked for deletion will never
be noticed. It will be eliminated completely if and when the user
finalizes deletions, without the user ever knowing that it was there.
Now that you have the basic idea of how it works, you can enter
the program and try it out. If you are puzzled by the code while you
are entering it, look at the more detailed discussion after the exercise.
You might want to modify the code in DATASCRN.FMT to create
part of the code in the GETDATA procedure. The data-entry screen
displayed by GETDATA is almost identical to the format screen that
was used previously. The only differences are that instructions about
paging through the database and about saving or discarding changes
have been removed, and that the instructions have been moved up a bit
to leave room below them for the questions that the program now asks
the user.
*PROCEDURE GETDATA
*new module for editing or appending data
*to be added to MAILPOW.PRG
*called by DATAMENU procedure
PROCEDURE getdata
PARAMETER mode
IF mode = "edit"
DO LOOKUP
ENDIF
CH. 12
READ
ENDIF
IF again = "Y"
LOOP
ELSE
EXIT
ENDIF
ENDDO
Company:
Telephone: (212)784-1059
CH. 12
A GENERAL-PURPOSE
PASSWORD PROCEDURE _
CH. 12
WITH “edit”. Then, if the password is not correct, the program will
skip the GETDATA procedure.
Once you have written PASSWORDQ, you can add the same
protection in the appropriate place in this same way in any program
you write, just by enclosing a command in IF password( ) and
ENDIF (after setting the PROCEDURE file).
With this background, you should have no trouble understanding
the password function, shown in Figure 12.10.
DO CASE
ENDCASE
***********************************
♦FUNCTION PASSWORD
*a general purpose password function
'k'k'k’k-k’k'k'k-k-k'k'k-k-k’k'k'k-k-k-k’k'k'k'k’k-k'k’k-k'k-k-k-k-k'k
FUNCTION password
PARAMETER mdoing
PRIVATE counter
counter = 0
DO WHILE counter < 3
CLEAR
mtry = SPACE(11)
@ 10, 20 SAY mdoing + " is password protected."
@ 12, 20 SAY "Enter the password > " GET mtry
READ
and so the loop is not executed again. The loop is simply followed by
an IF . . . ELSE statement, which returns .T. if the user got the
password right or returns .F. if the user got it wrong.
Try this password function out:
CH. 12
If you understand the password function in this form, then you are
ready to rewrite it in a form that makes it both a bit harder to under¬
stand and a bit more useful.
The one problem with the current function is that it is hard to
modify. To change the password, you must modify the words
“OPEN SESAME” in two places and probably also modify the
number of spaces that you give to mtry as its initial value. You can
solve this problem by using another variable, mright, to hold the cor¬
rect password, as shown in Figure 12.12.
Notice that, in this version of the program, you use initialize mtry
by using the function LENQ, which returns the length of a character
string: SPACE(LEN(mright)) returns a number of spaces equal to
the length of mright, no matter what the value of mright is, so that you
can now change the password without having to physically edit the
number of spaces displayed in the field where the user enters
the password. Likewise, the IF statements within the loop and at the
end of the program use the condition IF mtry = mright rather than
IF mtry = “OPEN SESAME”. Thus, it is now very easy to change
the password: you just need to modify the one line of code at the
beginning of the program that initializes mright.
USING AD VANCED PROGRAMMING TECHNIQUES 497
***********************************
♦FUNCTION PASSWORD
*a general purpose password function
***********************************
FUNCTION password
PARAMETER mdoing
counter = 0
DO WHILE counter < 3
CLEAR
mtry = SPACE(LEN(mright))
@ 10, 20 SAY mdoing + " is password protected."
@ 12, 20 SAY "Enter the password > " GET mtry
READ
IF mtry = mright
EXIT
ELSE
? CHR(7)
counter = counter + 1
LOOP
ENDIF
ENDDO
IF mtry = mright
RETURN .T.
ELSE
RETURN .F.
ENDIF
CH. 12
L - Labels
n E - Export for mail merge
K>-y
Q - Quit MAILPOWER!
NZCt
4 M
FP A, A I
What is your choice >
Mi-
Dil
r'fi
t i]
T) C
Figure 12.14: The Trace window.
aS§ Uj i fjpO-Aj
n< THE 'TRU
CH. 12
There is one other trick that you will find useful if you want to dis¬
tribute your programs as stand-alone applications. Rather than start¬
ing FoxPro and entering DO MAILPOW in the Command window
(or selecting Do from the Program menu), you can run your pro¬
gram directly from the operating system. All you have to do is enter
the command FOXPRO MAILPOW at the DOS Prompt to start
FoxPro and immediately execute the MAILPOW program. If you
enter this command, FoxPro will display its title screens for a
moment, but it will not display its Command window or menu bar:
instead, it will go directly to the Mail Power! main menu.
Of course, like any You can even relieve your user of the trouble of entering the word
other DOS com¬
mand, a batch command
FOXPRO as part of the command, by creating a DOS batch file. If
must be in the current you create a plain text file with the extension .BAT, DOS will exe¬
directory or on the search cute all the commands in that file when its name is entered. Thus,
path to be executed.
you can create a file named MAILPOW.BAT which has only the
command
FOXPRO MAILPOW
in it. When the user enters MAILPOW at the DOS prompt, DOS
will execute the command in the .BAT file and will start FoxPro and
immediately execute the Mail Power! program. (You can also add
commands to the .BAT file to do things such as automatically mak¬
ing the right directory into the current directory before executing the
program: for more information, see any intermediate or advanced
book on using DOS.)
Remember that you wrote the Main Menu module of Mail
Power! with the command QUIT at the end. Initially, you made this
command a comment, but if you delete the asterisk, then the pro¬
gram will execute the command and return to DOS as soon as the
user selects Quit from its main menu.
If you write a .BAT file so that users can just enter MAILPOW at
the DOS prompt to run the program, and if you include QUIT so the
user returns to the DOS prompt immediately after quitting the pro¬
gram, you will have made Mail Power! into a stand-alone program,
which is totally independent of FoxPro.
There is a FoxPro run-time module which you can use to run
stand-alone programs of this sort. A run-time module lets you dis¬
tribute your custom stand-alone programs to users who do not own
USING AD VANCED PROGRAMMING TECHNIQUES 501
To protect the code FoxPro. You must purchase the run-time module once, and then you
of programs that have the right to copy it and distribute it with your programs.
you distribute, you can
enter the command SET
You now have all the background in basic programming tech¬
ECHO OFF as the first niques that you need to write this sort of program. Though FoxPro
line of code in the pro¬ has many specialized commands and functions that we did not cover,
gram. Then users will not
this book did give you a very strong background in structured pro¬
be able to use the Trace
window to see the source gramming, and you should be able to apply the techniques you
code of the compiled learned to any programming problem that you need to solve.
program that you
Appendix C discusses some FoxPro commands that you have not
distribute.
learned yet, and your FoxPro Commands and Functions reference book
discusses the specialized commands that are used for working with
windows, pop-up menus, low-level file input/output, and many
other advanced capabilities of the FoxPro language. The Commands
and Functions reference includes sample programs using the more
difficult commands. Like any brief samples, though, these sample
programs can teach you to use these commands but cannot teach you
to use a large number of commands to build a complex program. The
background in structured programming that you have gotten in this
book will let you use any of these commands in your own work.
Figure 12.15 shows the final listing of the entire program. As an
exercise in structured programming technique, you might want to
rewrite the LOOKUP module as a user-defined function. Instead of
having it move the pointer to make EOF() true, have it return the
value of .T. if the record is found and .F. if the record is not found:
have the module ihat calls it use IF LOOKUP() rather than DO
LOOKUP with IF .NOT. EOF(). This is a much more elegant tech¬
nique and a step toward advanced programming.
★★★***********************************************
* MAILPOW.PRG
* a menu-driven, general purpose mailing-list program
CH. 12
CLOSE DATABASES
SET TALK ON
SET BELL ON
SET DELETED OFF
♦QUIT
**************************************************
*DATAMENU procedure
*The Data submenu for Mail Power
♦called by the main module
**************************************************
PROCEDURE datamenu
DO WHILE .T.
CH. 12
•ic'kic'k’kic'k'k'k'k-k'k'klt'k'k-kleic'kic'k-k’k-iclclc'k-k’k'kic'k'k'klc-k'k'k'k'klc'k'k'k'k'k-kls'k
*REPTMENU procedure
*The report submenu for Mail Power
*called by the main module
**************************************************
PROCEDURE reptmenu
DO WHILE .T.
ENDDO
RETURN
**************************************************
*LABLMENU procedure
*The label submenu for Mail Power
*called by the main module
**************************************************
PROCEDURE lablmenu
DO WHILE .T.
ENDDO
RETURN
CH. 12
**************************************************
*EXPTMENU procedure
*The export submenu for Mail Power
*called by the main module
PROCEDURE exptmenu
DO WHILE .T.
ENDDO
RETURN
**************************************************
* LOOKUP procedure
* lookup a record for editing, deleting or displaying data
* called by the DATAMENU procedure
**************************************************
PROCEDURE LOOKUP
mlookfor = SPACE(20)
* -trim blanks, in case the user did not enter whole name
* -or entered leading blanks by mistake
mlookfor = ALLTRIM(mlookfor)
CH. 12
mconfirm = "
6 14,18 SAY Is this the record you want (y/n)?
GET mconfirm
READ
******************************************
*PROCEDURE SCRNHEAD
*a general purpose screen header
‘called by the MAIN program and by
‘procedures DATAMENU, REPTMENU, LABLMENU, EXPTMENU, LOOKUP
PROCEDURE scrnhead
PARAMETER menuname
CLEAR
@ 0,0 SAY "MAILPOWER1 " + menuname
@ 0,70 SAY DATE()
@ 1,0 SAY "_
il II
**********************************
‘PROCEDURE GETDATA
‘new module for editing or appending data
‘to be added to MAILPOW.PRG
‘called by DATAMENU procedure
■k-k'kie-k-k'k'k'kic'kicieit'kicieick'k'k'k-k'k'k'kicie-k'k'k'kie
PROCEDURE getdata
PARAMETER mode
ENDIF
IF mode = "edit"
DO LOOKUP
ENDIF
„,
+ "-.
14,15 SAY "| <- -> : Move cursor within";
+" field |
15,15 SAY
+" |
16,15 SAY "| Tab Shift-Tab : Move cursor to ";
+"next/last field |
17,15 SAY " ________ " •
r
+
CH. 12
READ
ELSE
@ 21, 15 SAY "The changes will be discarded."
IF mode = "append"
DELETE
ENDIF
ENDIF
ENDIF
IF again = "Y”
LOOP
ELSE
EXIT
ENDIF
ENDDO
***********************************
★FUNCTION PASSWORD
★a general purpose password function
***********************************
FUNCTION password
PARAMETER mdoing
counter = 0
DO WHILE counter < 3
CLEAR
mtry = SPACE(LEN(mright))
@ 10, 20 SAY mdoing + " is password protected."
@ 12, 20 SAY "Enter the password > " GET mtry
READ
IF mtry = mright
EXIT
ELSE
? CHR(7)
counter = counter + 1
LOOP
ENDIF
ENDDO
IF mtry = mright
RETURN .T.
ELSE
RETURN .F.
ENDIF
WmK0SS$
ill
514 MASTERING FOXPRO
APP. A
1. Make sure you are logged into your hard disk. If you are not,
enter the command C: (do not forget to include the colon
after the disk letter). You can be in any subdirectory of the
hard drive.
If you do not have more than 1 megabyte of free disk space when
you are running FoxPrp, it might terminate abnormally and return
you to DOS. This would most likely occur when you are editing files
or programs, which requires extensive use of temporary files. For
INSTALLING FOXPRO 515
other operations, though, this would happen very rarely, even if you
have only half a megabyte free.
Before installing FoxPro, you also need two things that came with
the program:
1. If you have not already done so, make sure you are logged
into your hard drive. If your hard drive is drive C, enter the
command C: to make that the current drive. Make sure you
are in the root directory: if you are not sure what subdirec¬
tory you are in, enter the command CD \ to move to the root
directory. (The backslash stands for the root directory.)
2. Type MD \FOXPRO to make a new directory named FOX¬
PRO under the root directory.
9. Press the space bar to select the Help hie, which is currently
underlined. (If you are short of disk space, you can press the
down arrow to move the underline to the small Help hie and
then press the space bar; if you are very short of disk space,
do not select either.) Note that the word YES appears to its
right to indicate that it has been selected.
10. Press the down arrow key to move the underline to FoxView,
the screen and applications design tool, and press the space
bar to select it.
11. Press the down arrow key to move the underline to Compiled
Template, which is used when you generate code with Fox-
View, and press the space bar to select it.
12 If you decide that you want any other optional features, select
them in the same way. If you have a color monitor, you
should select color sets.
13. After you have selected all the options you want, press Enter
to install everything you have selected. FoxPro asks you for
confirmation: press Enter to install or N to abort. As it is
installing the optional features, FoxPro will ask you to insert
other disks: follow its instructions by inserting the appropri¬
ate disk and pressing any key to continue. For FoxView, it
will again ask for your monitor type and name, since Fox¬
View is a separate product that has been integrated with
FoxPro. Enter them as you did in Step 7 above.
518 MASTERING FOXPRO
APP. A
14. After the optional products are installed, FoxPro will display
a message saying FoxPro Installation Complete and will
return you to the DOS prompt. Remove the installation disk
from the A: drive. You are now in the FOXPRO directory of
your hard drive, which you created before installation. If you
want to see the files you have installed, enter DIR.
2. Enter DIR. Make sure that this is the DEMO director)7 and
that it includes files such as DEMO.DBF.
Finally, before using FoxPro, you should change the PATH com¬
mand in your AUTOEXEC.BAT file. This is the file in your root
directory which contains a list of commands that DOS automatically
executes whenever you start your computer.
A PATH command determines which directories the system looks
in when you enter a command at the DOS prompt. DOS always
looks in the current directory, and then looks in any directories listed
in the PATH command. For example, consider this typical PATH
command:
PATH C:;C:\DOS;C:\UTIL;C:\WP50;C:\FOXPRO
INSTALLING FOXPRO 519
If you have this file, use any word processor or text editor that
can edit plain ASCII files (which some word processors call
DOS files) to change it. If you do not have this file, you
should create one, again using any editor that can create
ASCII files.
APP. A
liiiiiiiliiliiiiiiai
' . i .
:
fggg^j|p||g§g^$§||^gPl
1111
522 MASTERING FOXPRO
APP. B
THE FILER _
The filer is a file management utility that can perform most of the
functions of the DOS operating sytems. Because DOS is based on
procedural commands that are difficult to learn, many commercial
programs have been developed that act as menu-driven substitutes
for it. The filer replaces DOS with a system that uses text buttons,
text boxes, scrollable lists, and the other interface features that you
should be very comfortable with after having used FoxPro. It is also
much more powerful than DOS.
The filer has two panels. Its Files panel lets you work with individ¬
ual files. Its Tree panel lets you work with the entire subdirectory sys¬
tem, so you can manipulate all the hies in a directory or a group of
directories.
When you are using the filer, you can move between these panels
in two ways. Each has a text button in its lower right corner that lets
you toggle to the other: select the Files or Tree text button of the
respective panels to toggle between panels. When you are using
the filer, a Filer menu pad is added to the menu bar: the last option
on its menu popup lets you move to the panel you are not using.
Depending on which panel you are using, select Tree Panel or Filer
Panel from the Filer popup in order to toggle between the two.
THE FOXPRO FILER AND DESK TOP UTILITIES 523
You can start the filer by selecting Filer from the System menu or
by entering FILER in the Command window. When you first start it,
the Files panel appears: since this is the default panel of the filer, we
will discuss it first.
APR B
easy to change them using the Attr text button or via a menu selec¬
tion: attributes will be discussed in detail when these selections are
discussed.
The two popup controls in the filer also work like the popup con¬
trols that you have seen in the Open and Save As dialog boxes. The
Drv popup lets you change the drive—for example, you can select A:
to make floppy disk drive A the current drive. The Dir popup control
lets you move quickly through a directory structure that is many lev¬
els deep, by letting you select any subdirectory, up to the root direc¬
tory, from the popup rather than repeatedly selecting the parent
directory from the scrollable list.
The text box labeled Files Like (under the Dir popup control) lets
you use a scrollable list that displays only some of the files in the cur¬
rent directory. The default setting for Files Like is *. *, which displays
all files, but you can specify files to be displayed by using literal char¬
acters in combination with the two DOS wild-card characters:
The file name and extension are two different words, so that *.*
represents any name followed by any extension. If you wanted to list
only your FoxPro database files, you could enter *.DBF in this text
box, so files with any name followed by the DBF extension would be
listed. If you have a group of files that you gave names beginning
with the letter J, you could list them all by entering J??????. * in this
text box.
You can combine more than one specification in this box if you
separate them with semicolons. For example, you could enter
*.DBF;*.DBT;*.FPT to list all database files and any associated memo
files (including both FoxPro and the older dBASE compatible
memo hies). Do not leave a space after the semicolon.
TAGGING FILES
The process of tagging hies is the key to using the hler. Tagging
simply means selecting a hie in such a way as to make a triangle
marker appear to the left of its hie name. Most text buttons or menu
526 MASTERING FOXPRO
APP. B
selections work only on files that are tagged. If no file is tagged when
you select them, they will simply display an error message.
Tagging Groups of Files The filer also contains three text buttons
that let you tag and untag groups of files; there are three menu
options that are identical to these text buttons.
• Tag All: tags all the hies that are displayed in the scrollable
list. This option is most useful if you use it in combination
with the Files Like text box. For example, enter *.DBF in the
Files Like text box, so that your database hies are displayed;
then select Tag All to tag all the database hies.
• Tag None: removes tags from all hies in all directories. Unlike
Tag All, Tag None does not work only on displayed hies—it
works on all hies in all directories. Use it to make sure that
you do not have any hies tagged that you do not know about.
• Invert: removes tags from all tagged hies, and tags all un¬
tagged hies in the current directory. For example, if you want
to delete all except the database hies in the current directory,
THE FOXPRO FILER AND DESKTOP UTILITIES 527
you can tag the database files and then select Invert. The
database files will be untagged and all the other files will be
tagged, at which point you can then select Delete.
You can also tag more than one file at a time by selecting the Find
text button (or menu option), described in the next section.
FIND
Selecting the Find text button or selecting Find from the Filer
menu calls up the Find dialog box, shown in Figure B.3.
[..]
01252061
06-Nov-90 1:27a .... Q Drv.
0125285D
01261E1F Find and tag files which have names like
ANSWER5
ANSWER5
CALNAMES
DATAENTR [ ] Specify text to search for...
DATAENTR
DATES [ ] gearch subdirectories
EMPLIST
EMPLIST « Sind * < gancel >
< Firid > < Copy > < Move > < Delete >
< Edit > < Attr > < Rename > < Size >
The Find dialog box lets you tag files based either on their names
or on their content. It can search in just the current directory or in a
number of directories.
The simplest way to use Find is to fill in the text box in the same
way that you do the Files Like text box of the Filer dialog box. As you
can see in the illustration, this box contains *.* by default, which
means it matches all files unless you instruct it to do otherwise. You
can fill it out with the wild-card characters (* and ?) and literal
528 MASTERING FOXPRO
APP. B
characters just as you learned to do with the Files Like text box in the
previous section.
Even if you are just searching for file names in this way, though,
the Find dialog box does more than the Files Like text box, because
you can select its Search Subdirectories check box to find matching
files in all subdirectories under the current directory. If you want to
search all the directories in the current drive, just make the root direc¬
tory the current directory before beginning the search. For example,
if you make the root directory the current directory, enter *.DBF in
the text box, and check the Search Subdirectories check box, you can
tag all the database files in all the directories of the current disk drive.
You can also use Find to search text files. It will tag those that con¬
tain text that you specify. If you select the Specify Text To Search For
check box, you will call up the dialog box shown in Figure B.4.
Name
Though you cannot see them in the illustration, there are three
text boxes under the words “of the following strings, ’ ’ where you can
fill in the character strings that you want to search for.
The Any and All radio buttons are useful if you fill in more than
one of these text boxes: they let you specify whether the file or files
THE FOXPRO FILER AND DESKTOP UTILITIES 529
COPY
Selecting the Copy text button, or Copy from the Filer menu, calls
up the Copy dialog box, shown in Figure B.5.
This dialog box lets you copy tagged files. Copying a file preserves
the original file and creates a duplicate of it that either has another
name or is in another location.
Remember that the files must be tagged before you call up the
Copy dialog box.
530 MASTERING FOXPRO
APP. B
EMPLI
EMPLI
Copy < Cancel >
< Find
< Edit > < Attr > < Rename > < Size > < Tree >
The Copy Tagged Files As text box, at the top of this dialog box,
lets you specify the name of the file. The default, *. *, keeps the origi¬
nal name of the file. You can change the name by adding literals
instead of the wild-card characters. For example, if you want to make
backups of tagged files, you can enter *.BAK in this text box: all the
tagged files will be copied to files with the same name except for
the .BAK extension.
The target directory text button and text box let you specify the direc¬
tory that you want the copies of the file to be in. If you select this text but¬
ton, you will call up the Select Target Directory dialog box, shown in
Figure B.6. As you can see, this dialog box works like the Open or Save
As dialog box: it lets you use a scrollable list to move to the parent or chil¬
dren directories of the current directory; the Directory popup control
lets you move quickly up and down the subdirectory tree; and the Drive
popup control lets you select the disk drive. Alternately, you can just
type the disk and directory in the text box to the right of this text button.
Notice that the default target directory is the current directory; you
have also seen that the default is for the copies to have the original files’
names. You must change one of these defaults. You can copy files to
another directory or disk while keeping their current names, or you can
THE FOXPRO FILER AND DESKTOP UTILITIES 531
Name
Select Target Directory
[..] C:\MAILPOW c
00280
00280 [■ J Drive
00282
►ANSWE
ANSWE
Co
<fl
MAILP0W1
MAILP0W2
[MAILP0W3
]_
CALNA Directory MAILPOW
DATAE
DATAE
DATES « Select »
EMPLI
EMPLI < Open >
—
< Find < Cancel >
< Edit > >
copy files in the current directory with different names, but you cannot
have two files with the same name in the same directory.
If you check the Replace Existing Files check box of this dialog
box, the files produced by the COPY command will overwrite exist¬
ing files with the same names without giving you any warning. If you
do not check this check box, the command will display an alert before
it overwrites a file. After you select Yes or No to determine whether
that file will be overwritten, the command will go on and copy the
rest of the tagged files.
If you check the Preserve Directories check box, the command will
copy the directory structure as well as the files that are tagged. If this
check box is not checked, tagged files from various subdirectories will
all be copied into a single subdirectory. This feature will be explained
in the discussion of the filer’s Tree panel.
MOVE
Selecting the Move text button, or Move from the Filer menu,
calls up the Move dialog box, shown in Figure B.7.
532 MASTERING FOXPRO
APP. B
Move is like Copy, except for one point. Copy creates a duplicate
file and preserves the original; Move creates a duplicate file and elim¬
inates the original.
As you can see, the Move dialog box looks exactly like the Copy
dialog box, and all of its features function in the same way. The only
difference is that, after you enter all of the specifications and select
Move, the original file is eliminated. The effect is that the file is
moved from its current location to the specified location; it is not just
copied at the specified location.
DELETE
Selecting the Delete text button, or Delete from the Filer menu,
calls up the Delete dialog box, shown in Figure B.8.
This dialog box asks you to confirm that you want to delete each of
the tagged files. Select Delete to delete the one file whose name is dis¬
played. Select Skip to retain the file whose name is displayed; the dia¬
log box will go on and ask you about deleting any other tagged files.
Select Delete All to avoid this file-by-file confirmation process and
delete all tagged files immediately. Needless to say, you should use
Delete All with caution.
THE FOXPRO FILER AND DESKTOP UTILITIES 533
SORT
Selecting the Sort text button or Sort from the Filer menu calls up
the Sort dialog box, shown in Figure B.9.
< Find > < Copy > < Move > < Delete > Sort >
< Edit > < Attr > < Rename > < Size > < Tree >
[..]
00280325
06-NOV-90 1:27a 1 Drv.
00280B16
00282223 Select Sort Criteria LEARNFOX
►ANSWER5 .DBF
ANSWERS . FPT ame
CALNAMES . IDX tension (•) 0scendlng Like
DATAENTR . FMT lze
DATAENTR . PRX ( ) descending
DATES .IDX Attributes ag All >
EMPLIST .DBF ag None >
EMPLIST .FPT « gjK » < gancel > Invert >
< Find > < Copy > < Move > < Delete >
< Edit > < Attr > < Rename > < Size > Tree
APP. B
This dialog box lets you change the order in which files are dis¬
played in the filer’s scrollable list. As you can see, the radio buttons
Name and Ascending are checked by default, so that the files are dis¬
played alphabetically by name.
You can also select radio buttons to display the files in the order
determined by their extension, size, date, or attributes. (Attributes
will be discussed later in this appendix.) The most useful of these is
Extension: it is often handy to sort by extension so that files of the
same type (database files, index files, program files, and so on) are
grouped together.
The other two radio buttons let you choose ascending or descend¬
ing order. You might want to choose Descending in order to have the
most recent dates come first, or to have the largest files come first.
EDIT
Selecting Edit opens edit windows for all tagged files.
You might find this useful, for example, if you want to open edit
windows for all your program files. You could enter *.PRG in the
Files Like text box and then select Tag All to tag all program files,
then simply select Edit to open edit windows for all these files. The
edit windows will appear to be stacked, and you can call any one for¬
ward to work on it.
ATTR
Selecting the Attr text button, or Attr from the Filer menu, calls up
the Attributes dialog box, shown in Figure B.10.
These attributes are represented by letters in the Attr column of
the file list.
An r in this column means that the file is Read Only: a user can
read the hie but cannot delete, edit, or otherwise modify it.
An a in this column means that the hie is newly created or has been
modihed since it was last backed up. Most backup programs back up
only hies that have this attribute and switch this attribute off so they
do not copy them again the next time they do a backup. The attribute
is switched on again if the hie is modihed.
THE FOXPRO FILER AND DESKTOP UTILITIES 535
Changing the sys¬ An h in this column means that the hie is a hidden hie, which does
tem or the hidden not appear in an ordinary DOS directory. DOS includes two hidden
attribute can let you
create later errors that
hies in the root directory, IBMBIO.COM and IBMDOS.COM;
prevent your operating you have not seen these in your root directory, but you can see them,
system from working. with the h attribute, if you use the hler to look at your root directory.
An s in this column means that the hie is a system hie. There are
several key DOS hies that are protected with this attribute, because
they must have a specihc location on the disk. The hler does not let
you move, delete, rename, or overwrite a hie with this attribute.
You can alter any of these attributes by selecting the appropriate
check box. Then, if you select the Change text button, FoxPro will
ask you to conhrm that you want to make this change to each of the
tagged hies. If you select Change All, FoxPro will change all tagged
hies without this conhrmation process.
RENAME
Selecting the Rename text button, or Rename from the Filer
menu, calls up the Rename dialog box, shown in Figure B. 11.
536 MASTERING FOXPRO
APP. B
[..]
00280325
00280B16
002D2Fp-
01332D
06-NOV-90
27-Feb-91
27-Feb-91
1:27a
12:40a
12:40a
. a.
. a. 1 Drv.
«]
►ANSWER Rename: ANSWER5.DBF
ANSWER
CALNAM To:
DATAEN
DATAEN * Rename » < Cancel >
dates l—
EMPLIST .DBF 1738 07-Feb-91 10:33a .a.
1 Invert
< Find > < Copy > Move < Delete > Sort
< Edit > < Attr > < Rename > < Size > Tree
To rename a file, simply fill in the new name in the text box of this
dialog box and select Rename. The current file name appears in
the dialog box by default, in case you want to give the new file a simi¬
lar name. The dialog box lets you rename all of the tagged files
in turn.
If another file already has the new name you want to give to a file,
an alert will appear, saying you have made an error: You cannot use
Rename to give a file a name that is already used. The alert asks you
to choose Yes if you want to continue renaming other tagged files or
No if you want to cancel the process and return to the Files panel.
SIZE
Selecting the Size text button, or Size from the Filer menu, calls up
the Size dialog box, shown in Figure B.12.
This dialog box simply displays information about tagged files,
including the number of hies currently tagged, their total size in
bytes, and the amount of space they occupy on the disk in clusters
and bytes.
The number of bytes the hies occupy on the disk is greater than the
number of bytes in the hies themselves, because disk space is broken
THE FOXPRO FILER AND DESKTOP UTILITIES 537
[..]
00280325
00280B16 Tagged File Statistics
002D2F0F
01332D1E Files: 1
►ANSWER5 .DBF Bytes: 778
ANSWER5 • FPT les Like
CALNAMES . IDX Actual space occupied: *.*
DATAENTR . FMT
DATAENTR . PRX Clusters: 1 < Tag All >
DATES .IDX Bytes: 4,096 < Tag None >
EMPLIST .DBF < Invert >
QK
< Find > < Copy < Sort >
< Edit > < Attr < Tree >
APP. B
Drv .
-BIN
-CSBOOK
-FOXPRO
1-TEMPLCOD
-FPBOOK
-LEARNFOX Files: 587
-MAILPOW Used: 9,379,840
—MAILP0W1 Free: 1,212,416
-MAILPOW2
-MAILPQW3
-MISC
TAGGING DIRECTORIES
You must tag the directories that you manipulate with the Tree
panel just as you tag the hies that you manipulate with the Files
panel. As with the Files panel, a triangle appears to the left of a direc¬
tory that is tagged in the Tree panel.
RENAME
Selecting the Rename text button or selecting Rename from the
Filer menu calls up the Rename dialog box, shown in Figure B.14.
THE FOXPRO FILER AND DESKTOP UTILITIES 539
This dialog box renames the tagged directories, and works just like
the dialog box that is used for renaming files. Fill in the new name in
its text box: the current name appears as the default, in case you want
to use a similar name. If multiple subdirectories are tagged, the filer
lets you rename them all in sequence.
CHDIR
Selecting the Chdir text button or selecting Chdir from the Filer
menu lets you change the current directory. Simply tag the directory
that you want as the current directory, and make this selection. The
bullet that shows which directory is the current directory will move to
indicate the change.
MKDIR
Selecting the Mkdir text button or selecting Mkdir from the Filer
menu calls up the Mkdir dialog box, shown in Figure B. 15.
To create a new subdirectory under the current directory, simply
enter the name you want to give it and select Mkdir.
540 MASTERING FOXPRO
APP. B
I
C: Drv.
-BIN
-CSBOOK
-F0
—MI
E « Mkdir » <Cancel >
COPY
Selecting the Copy text button, or Copy from the Filer menu, calls
up the Copy dialog box, shown in Figure B. 16.
This dialog box is like the one that you use to copy files, and it is
used the same way, except that it copies all the hies of the directories
that are tagged when you use it from the Tree panel.
The Preserve Directories check box becomes useful in this panel. If
you do not check it, all the hies in tagged directories will be copied
into a single target directory. If you do check it, the hler will create a
subdirectory structure under the target directory that corresponds to
the structure of tagged subdirectories under the highest tagged direc¬
tory . The hies in the highest tagged directory will be copied into the
target directory, but hies in the directories under it will be copied into
separate, newly created subdirectories with the same names as their
original directories.
MOVE
Selecting the Move text button, or Move from the Filer menu,
calls up the Move dialog box, shown in Figure B.17.
THE FOXPRO FILER AND DESKTOP UTILITIES 541
C: 1 Drv.
[ 3 1jeplace
< existing files
L J lireserve directories 87
40
16
As in the Files panel, the Move option of the Tree panel is identical
to the Copy option, except that the original files are deleted and only
the copies in the new locations are left.
542 MASTERING FOXPRO
APP. B
DELETE
Selecting the Delete text button, or Delete from the Filer menu,
calls up the Delete dialog box, shown in Figure B.18.
Use this feature This dialog box looks like the one that the Files panel uses to delete
with extreme cau¬ files, but there is one vital difference. The one in the Files panel lets
tion, as you cannot see
you confirm the deletion of each file that is tagged; this one only
the names of the files
in the directories that lets you confirm the deletion of each directory that is tagged. Select
you are deleting. Delete to confirm the deletion of the directory, or Skip to skip it and
make the filer continue with the next directory.
—FO
1_ Delete directory: C:\LEARNFOX
—FP
—LE
—MA
El Delete files only
X] Remove all sub-directories
587
,840
,416
t «|]elete » < j§kip > <Delete 011 > <gancel >
t
You do not need to tag the subdirectories individually: just tag the
single directory at the top of the group that you want to delete and use
this check box.
The fact that this check box is checked by default makes it very
dangerous. If you mistakenly tag your root directory and then select
Delete All without changing the default setting of the check boxes,
the filer can delete every file and every directory of your hard disk.
SIZE
Selecting the Size text button or selecting Size from the Filer menu
calls up the Size dialog box, shown in Figure B. 19.
C:
C
-BIN
-CSBOOK Tagged Directory Statistics
-FOXPRO
1-TEMPLCOD Files: 102
-FPBOOK Bytes: 164,541
-LEARNFOX les : 587
-MAILPOW Actual space occupied: ed: 9,379,840
-MAILP0W1 ee: 1,212,416
-MAILP0W2 Clusters: 118
-MAILP0W3 Bytes: 485,328
-MISC
« 0k »
<Rename> <Chdir
< Move > < Delete >
As you can see, this dialog box is gives you basic statistics about the
number of hies in the tagged directories, their size, and the number
of clusters and actual disk space they occupy, just like the dialog box
that appears when you select Size from the Files panel.
FILES
Selecting the Files text button on the lower right, or selecting Files
Panel from the Filer menu, brings you back to the Files panel.
544 MASTERING FOXPRO
APP. B
The filer is the most elaborate utility included with FoxPro, but the
System menu also includes a number of desktop utilities similar to
the ones included in other popular programs. These utilities are
meant to replace items that ordinarily clutter up your desk, such as a
calculator and an appointment calendar.
THE CALCULATOR
Selecting Calculator from the System menu calls up the calculator,
shown in Figure B.20.
MC 7 8 9 / -f
MR 4 5 6 * %
M+ 1 2 3 - C
M- 0 ± + =
Table B. 1: Special Keys for Using the FoxPro Calculator with the Keyboard
Q square root
N plus or minus ±
A add to memory M+
value
S subtract from M-
memory value
R recall memory MR
Z clear memory MC
The discussion below talks about typing and using numbers, oper¬
ators, and calculator functions. In every case, this means either
selecting them with the mouse or typing them using the keyboard
and the special keys listed in the table.
The functions of the calculator keys will probably be familiar to you.
The number keys and the decimal point are, of course, used to
enter numbers. Simply type in the number and it will appear on the
display panel on the top of the calculator.
The arithmetic operator keys + , - , *, and / are used to indicate
addition, subtraction, multiplication, and division. To perform these
operations, type the first number, then type the operator (when you
type the operator, the first number that you typed will be highlighted
in the display panel to indicate that it is fully entered, and the opera¬
tor that you typed will appear to its right), then type the second num¬
ber. Once the second number is on the display panel, type = to
complete the calculation.
To find a square root, first type the number. When it is displayed
correctly, use the square root operator. The result will be displayed in
the display panel immediately.
The percent operator lets you perform operations that use some
percentage of the number in the display panel. For example, to find
a number 10 percent larger than a given number, first type the given
number, and when it is in the display panel, type + , then type 10,
then use % . A number 10 percent larger than the original number is
displayed.
546 MASTERING FOXPRO
APP. B
the keypad available to you whenever you use the calculator. You
can make your choice from three radio buttons:
The other set of radio buttons lets you adjust how decimals are dis¬
played. It also includes three choices:
THE CALENDAR/DIARY
Selecting Calendar/Diary from the System menu calls up the
Calendar/Diary window, which is shown in Figure B.21 along with
the related Diary menu popup.
548 MASTERING FOXPRO
APP. B
17 18 19 20 21 22 23 delete...
24 25 26 27 28 29 30
31
<<-M><M+><<-Y><Y*> <Todav>
• using the mouse, simply click on the panel that you want to
move to
THE FOXPRO FILER AND DESK TOP UTILITIES 549
When the Diary panel is active, use the usual editing techniques to
make diary entries. They may be of any length, and you can scroll
through them in the usual ways or resize or zoom the Calendar/"
Diary window to see more of an entry.
When the Calendar panel is active, move among the days of the
current month by using the arrow keys or (if you have a mouse) sim¬
ply by clicking the day that you want. To move to a different month,
either use the text buttons at the bottom of the Calendar panel, the
corresponding options on the Diary menu, or the hot keys, as follows:
• The M“* text button, the Ahead Month option on the Diary
menu, or the PgDn key moves you forward a month.
• The *~Y text button, the Back Year option on the Diary
menu, or the Shift-PgUp key combination moves you back
a year.
• The Y-* text button, the Ahead Year option on the Diary
menu, or the Shift-PgDn key combination moves you for¬
ward a year.
In addition, the Today text button, the Today option on the Diary
menu, or the T key moves you back to the current date, no matter
where you are in the calendar when you select it.
The Delete option of the Diary menu lets you delete all entries in
the Diary prior to the date selected on the Calendar. It presents you
with a warning before deleting this data, and the No text button is the
default choice. These should help you to avoid deleting data by mis¬
take. Select the Yes text button to confirm that you want to delete all
entries prior to the date selected on the calendar.
Use the usual editing techniques to delete the entry for a single day.
SPECIAL CHARACTERS
Selecting Special Characters from the System menu calls up the
Special Characters window, shown in Figure B.22.
550 MASTERING FOXPRO
APP. B
1 1 - Ik A j - k =L J 1 JL J
1 <• t 4- i A T ► i
■
linn ■ J 1 m r n *-
o i * ♦ * * • ■0 5 9 4 * *
C £ * A f % * ii SI § « » l : - ;
a p r TTE CT P T i 0 Q S ~ 0
£ n = ± * < -r ° vT n 2
aA aX X
a a. 1 l
a a CL e e e e 6 i 1 1 aj
0 6 6 6 6 U u U Li u y
2 o £
<E Q Q R R
making the special character appear, try holding down the Shift key
while you select it from the Special Characters window.
0 00 NUL
1 01 'A SOH
12 'B STX
17 'C ETX
U "D EOT
15 “E ENQ
06 T ACK
07 'G BEL
The first column shows the ASCII number of the character in deci¬
mal notation. The second column shows the same ASCII number in
hexadecimal (base 16) notation: if you do not know hexadecimal
notation, you can simply ignore this column, as it is not needed for
FoxPro programming. The third column shows the graphic repre¬
sentation of the character. (Most characters are shown as they are
printed, but the lower-number ASCII characters are control charac¬
ters, which are not printed, so they are represented by graphics—
such as a face.) The fourth column shows the Control-key combination
(if there is one) for the character. The fifth column represents the mean¬
ing of control characters (lower-number ASCII characters) in an
552 MASTERING FOXPRO
APP. B
APP. C
• the most useful of the commands and functions that were not
discussed in the text, such as the commands DECLARE and
DIMENSION, which are used for creating arrays, and the
function IIF(), which is used to build an IF statement into an
expression.
APP. C
COMMANDS _
* | && | NOTE
These commands are used to indicate a comment in a program:
text following them is ignored by FoxPro and is used to make the pro¬
gram easier for a programmer to understand.
* or NOTE must be at the far left of a line of text, and comments
must be to their right. Nothing else may be on the line except these
commands and comments.
&& may be anywhere on a line of the text: anything to its right is a
comment. Actual program code may be to its left.
.P |i ..pp
[, <.exp2> ...]
• V <num exp>: As you can see if you look at the full com¬
mand, a FUNCTION clause can contain either an ordinary
function template (which is a character expression) or the let¬
ter V followed by a number or numeric expression. V can be
used to limit the number of spaces on a line that the expres¬
sion occupies and to stretch it vertically instead. The numeric
expression is the maximum number of columns on a single
line that the expression can occupy: if it is longer, it will con¬
tinue on successive lines.
APP. C
@ <row, col>
[RANGE [<exp2'>][,<exp3'>]\
[DEFAULT <exp2>]
• RANCE [ < exp2 > ] [, < exp3 > ] can be u sed to specify a ran ge
of values within which character, numeric, or date input
must fall. The data type of the expressions used here depends
on the data type of the variable following GET. If the user
enters a value that does not fall between the two values in the
RANGE clause, an alert is displayed which includes
the required range. Either of the two expressions following
RANGE may be omitted and the clause will check only for
560 MASTERING FOXPRO
APP. C
values that are too low or high; if the single expression follow¬
ing it is preceded by a comma, it is read as the upper bound
of the range.
This command draws a box with < rowl >, Kcoll > as its upper left
corner and <row2>, <col2> as its lower right corner. Of course,
these all must be numeric expressions.
If rowl equals row2, a horizontal line is drawn. If coll equals col2,
a vertical line is drawn.
The optional character expression at the end lets you specify what
characters are used to draw the box. It consists of up to nine characters.
The first eight represent the upper left comer, top, upper right comer,
right edge, lower right comer, bottom, lower left comer, and left edge
of the box. (Notice that they begin with the upper left and move around
the box clockwise.) If a ninth character is added, it is used to fill the box.
You may specify these characters by ASCII number, using the CHRQ
function; alternately, the Special Characters window, described in
Appendix B, gives you an easy way of including actual extended DOS
line-drawing characters in your programs.
If the final character expression is omitted, the box is drawn with a
single line.
APP. C
APPEND
[BLANK]
This command lets you add data to the end of the current database
file. First you must open the file with the command USE <jile
name>. If you use this command when no file is open, the Open File
dialog box appears to let you choose a database file.
APPEND by itself opens a Browse/Change window, displaying a
blank record added at the end of the database file that is open in the
current work area, and moves the pointer to that record. If data is
entered in the record, that record becomes permanent and a new
blank record is added. An indefinite number of records are added as
needed.
APPEND BLANK adds a single blank record to the end of the
database file that is open in the current work area and moves the
pointer to that record. Character fields are initialized with spaces.
Numeric fields are initialized with zero. Date fields are initialized
with three pairs of spaces, for month, day, and year (or some permu¬
tation thereof), each separated with a slash. Logical fields are initial¬
ized with .F.
APPEND BLANK does not open a Browse/Change window.
Because the field values are initialized, they can be used in programs
as the basis of the variables in a series of @ <row >,<col> SAY <exp >
GET <variable> commands, and they can be filled using a series of
REPLACE commands.
ESSENTIAL COMMANDS AND FUNCTIONS 563
[FIELDS <fieldlist>]
This command lets you add data from another file to the end of the
database file that is open in the currently selected work area.
In the simplest form of the command, the data is appended from
another database file with a .DBF extension. You can specify the
name of the data file; FoxPro assumes a .DBF extension if none is
entered (unless a TYPE clause is included). Or you can use the ?
option, and FoxPro will display the Open File dialog box and let the
user select the file to Append from.
Several optional clauses offer other capabilities:
FIELDS <jield list> lets you select which fields in the database file
will have data appended to them.
FOR <log exp> lets you select which records in the other file will
be added to the database file that is currently open. Only records for
which the logical expression is evaluated as true are added.
TYPE SDF i DELIMITED [WITH <character> |BLANK|TAB]
lets you append data to the database file that is currently open from
files that are not FoxPro compatible database hies. The types of hies
you can append data from are
• SDF files: ASCII text hies where records have a fixed length
and a carriage return and line feed at the end.
AVERAGE
[FOR <logexp>]
[WHILE <logexp>]
BROWSE
[FORMAT]
[LAST]
[NOAPPEND]
[NOGLEAR]
[NODELETE]
[NOEDIT | NOMODIFY]
[NOFOLLOW]
[NOMENU]
[NORMAL]
[NOWAIT]
[SAVE]
APP. C
FIELDS <field list> makes the Browse window contain only the
fields mentioned in the field list. The field list may be made up of field
expressions as well as field names, so it may also include calculated
fields.
FORMAT lets you use a format file with an .FMT extension to
control the way the fields are displayed. The format hie must first be
made active with the command SET FORMAT TO <file name >.
FREEZE <field name> allows changes to be made only to the one
held that is mentioned, though all the helds are displayed.
LAST opens the Browse/Change window in the same configura¬
tion in which it was last used.
NOAPPEND makes it impossible to add new records to the hie.
NOCLEAR leaves the Browse/Change window visible on the
screen after you are done using it. (By default, the window disap¬
pears when you are done.)
NODELETE makes it impossible to mark records for deletion.
NOEDIT J NOMODIFY makes it impossible to make any changes
in the data.
NOFOLLOW makes the pointer stay where it is in the database
when you modify the held that the database is indexed on. (By
default, the pointer stays on the record, following that record to the
new position that it moves to because its key held was modihed.)
NOMENU makes the Browse/Change window open without the
Browse menu pad being added to the menu bar, so that the user can¬
not access the Browse menu popup.
NORMAL makes the Browse/Change window open with its nor¬
mal attributes even if it is opened in a user window. If this option is
not used, it takes its attributes, such as its colors and whether it can
grow or not, from the user window it is opened in.
NOWAIT makes a program continue without any pause after the
Browse/Change window is opened. If BROWSE is used in a program
without this option, the Browse/Change window is opened and the
program is suspended until it is closed.
PREFERENCE = <char exp> lets you save and reuse the attrib¬
utes of Browse windows. Unlike the LAST option, which only reuses
t e previous configuration, this option can reuse any configuration
used in the past. The first time BROWSE ,s used with this option with
a given character expression, the PREFERENCE referred to by that
name is created. When the window is closed, that PREFERENCE is
ESSENTIAL COMMANDS AND FUNCTIONS 567
updated. Any time in the future that the window is opened with that
PREFERENCE, it keeps the same configuration.
SAVE keeps the Browse/Change window (and an associated Memo
window, if one is open) on the screen after the user has exited from it.
This option can only be used in programs.
WIDTH <num exp> limits the width of the display of all fields.
Only the display is affected, not the actual data. You may use the
arrow fields to scroll through a field and see all its data. WINDOW
<window name> opens the Browse/Change within another window,
whose name is specified in the command. That window must first be
defined using the DEFINE WINDOW command. This option of the
BROWSE command activates that window and opens the Browse
window in it.
6-0 -Tc> f ‘ jTEiki Ke/ Vj?#3 '
J7l£/P/ J<£'/ '
CALCULA TE [< scope >y < math expr list >
[WHILE <logexp2>]
CHANGE
[NOAPPEND]
[NOCLEAR]
[NODELETE]
[NOEDIT]
[NOFOLLOW]
ESSENTIAL COMMANDS AND FUNCTIONS 569
[NOMENU]
CLEAR
This command clears the screen or the current output window,
leaving it blank.
CLEAR ALL
This command has four main effects:
• It closes any open database files, index files, format files, and
memo hies.
cjt,Mt< rizLUS
CLOSE
ALL |
ALTERNATE|
DATABASES |
FORMAT |
INDEX |
MEMO ALL |
PROCEDURE
APP. C
CONTINUE
This command finds the next record that matches the criterion of a
LOCATE FOR <logexp> command that has been used previously—
that is, the next record in the database file for which the logical
expression in the LOCATE FOR command is evaluated as true. If a
record is not found, EOF() is given the value of .T.
CONTINUE may be used repeatedly, until you reach the end of
the database hie (or the end of the LOCATE scope, if a scope clause
was used with the original LOCATE command).
[WHILE <,logexp2>\
This command copies the records in the database hie that is open
in the current work area, to the hie whose name is specihed.
In the simplest form of the command, the data is copied to another
database hie with a .DBF extension. You can specify the name of
the data hie; FoxPro assumes a .DBF extension if none is entered
(unless a TYPE clause is included).
Several optional clauses offer other capabilities:
<scope> lets you select which records will be copied: only records
in the specihed scope will be copied. If this clause is omitted, the
default scope is ALL.
FIELDS <field list> lets you select which helds in the database hie
will be copied.
FOR <logexp> or WHILE <logexp> let you select which records
will be copied. Only records for which the logical expression is evalu¬
ated as true are copied.
TYPE SDF | DELIMITED [WITH <character> |BLANK|TAB]
lets you copy data from the database hie that is currently open to hies
that are not FoxPro compatible database hies. The types of hies to
which you can copy data are
• SDF files: ASCII text hies where records have a fixed length
and a carriage return and line feed at the end.
COUNT
APP. C
[ <file name> \ ?]
This command lets you define the structure of a new database hie.
If you do not specify a hie name, the new hie will be named
UN III LED.DBF until you save it by selecting
File menu popup.
If you specify a file name, FoxPro assumes a .DBF extension.
If you use the ? option, FoxPro displays a dialog box that lets the
user enter the name of the new hie to be created
For more information on defining the structure of a database file,
see Chapter 2.
CREA TE LABEL
[Pfile namey- ] ?]
CREATE REPORT
[ Kfile name> | ?]
This command opens the report layout window to let you create a
new report form.
If you do not specify a file name, the new file that holds the label
form will be named UNTITLED.FRX until you save it by selecting
Save As from the File menu popup.
If you specify a file name, FoxPro assumes an .FRX extension.
If you use the ? option, FoxPro displays a dialog box that lets the
user enter the name of the new file to be created.
For more information on creating label forms, see Chapter 6.
APP. C
For example, if you have ten different interest rates that you need
Aknay AS
to use in a program, it could be confusing to give each a separate
7 7 * ** C ^ name. You might find it easier to create an array to hold them. I he
AiArf
/t'/rrr
command
DECLARE int_rate(10)
/fK/K '
~\ <A creates ten memory variables, named int_rate(l), int_rate(2),
INN
int_rate(3), and so on. You can then initialize these variables as you
ft) : ,6
do any memory variable: for example,
int_rate(1) = .1
/?7'/V
Pp
_
uses ten percent as the first interest rate.
tv
The data type of each variable in the array is determined when it is
fj\bx
H7/< t 9> initialized.
P
C/ y
n
l) A si r ) i
r If you add the optional second numeric expression following the
array, you will create a two-dimensional array that is referred to by
A
two index numbers. Let’s say that you have ten different interest
fj\£TVfih
rates for each month. You could use the command
AV DECLARE int_rate(12,10)
to create 120 memory variables. Then you could use the variable
int_rate( 1,1) to hold the lowest interest rate for January, the vari¬
able int_rate(l ,2) to hold the second interest rate for January, and so on
through int_rate(l, 10), which holds the highest interest rate for January.
Likewise, you could use the variable int_rate(2,1) to hold the low¬
est interest rate for February, the variable int_rate(2,2) to hold the
second interest rate for February, and so on through int_rate(2,10),
which holds the highest interest rate for February.
Arrays are particularly powerful because you can use variables
as the index number and access the entire array by altering the value
of the variable. If you use a DO WHILE loop to change the value of
the index number, you can print out hundreds of variables using just
a few lines of code.
ESSENTIAL COMMANDS AND FUNCTIONS 5 77
DELETE
APP. C
(, is -Tm af subscripts).
For cxa.rn.plc, if you have ten different interest rates that you need
i oAi^et&S t* MAAY A
7 to use in a program, it could be confusing to give each a separate
•T?j£ l£to(ZTH »F TftE name. You might find it easier to create an array to hold them. The
C60LP SF 6& • command
DIMENSION int_rate(10)
to
f\io A)(Tf flACM - creates ten memory variables, named int_rate(l), int_rate(2),
A )f
int_rate(3), and so on. You can then initialize these variables as you
U k£ ^U~. do any memory variable: for example,
n££ A7& ArY W lf uses ten percent as the first interest rate. The data type of each vari¬
able in the array is determined when it is initialized.
If you add the optional second numeric expression following the
array, you will create a two-dimensional array that is referred to by
two index numbers. Let’s say that you have ten different interest
rates for each month. You could use the command
to create 120 different memory variables. Then you could use the vari¬
able int_rate( 1,1) to hold the lowest interest rate for January, the
variable int_rate(l ,2) to hold the second interest rate for January, and so
on through int_rate(l,10), which holds the highest interest rate for Jan¬
uary. mice wise, you could use the variable int_rate(2,1) to hold the low¬
est interest rate for February, the variable int_rate(2,2) to hold the
second interest rate for February, and so on through int_rate(2,10),
which holds the highest interest rate for February.
Arrays are particularly powerful because you can use variables as
the index number and access the entire array by altering the value
of the variable. If you use a DO WHILE loop to change the value of
the index number, you can print out hundreds of variables using just
a few lines of code.
ESSENTIAL COMMANDS AND FUNCTIONS 579
DIR | DIRECTORY
In its simplest form, this command displays the names of all data¬
base files in the current directory, the number of records in each, the
date each was last modified, and the size of each in bytes.
If the command is used with a skeleton, though, it is more like the
DOS command DIR, displaying all the files specified by the skeleton. A
skeleton can be made up of literals and the two wild-card characters, *
which stands for any word, and ? which stands for any character. For
example, DIR *.* will list a directory of all files in the current subdirec¬
tory, and DIR *.TXT will list a directory of all files in the current direc¬
tory that have the .TXT extension.
The optional ON and LIKE clauses let you specify the drive or the
path name that you want a directory for, so that you can get a direc¬
tory that is not for the current drive and subdirectory. The words ON
and LIKE themselves are optional in these clauses.
The optional TO PRINT or TO FILE <file name> clause lets you
send the directory listing to the printer or to the text file whose name
is specified.
DISPLA Y
[OFF]
In its simplest form, this command displays the contents of the cur¬
rent record on the screen.
580 MASTERING FOXPRO
APP. C
DISPLA Y STRUCTURE
[IN <alias>]
DO CASE
[OTHERWISE
... ]
ENDCASE
ENDO
This command lets you execute a block of program code repeat¬
edly. The code between DO WHILE and ENDDO will be executed
as long as the logical expression is true. This is called a loop.
If the expression is untrue when the program first reached the DO
WHILE statement, the program will simply skip all these lines of
code and continue with the line that follows the ENDDO. If the
expression is true, the program will execute all these lines of code.
When it reaches ENDDO, it will go back to the DO WHILE state¬
ment and check again to see if the condition is true. If so, it will exe¬
cute the code again; if not, it will continue with the line following
ENDDO
Normally you would have some code within the loop that ulti¬
mately makes the logical expression false, so that the code is executed
a finite number of times. Alternately, you can use the command
EXIT to break out of the loop. An infinite loop is a common pro¬
gramming error.
The command EXIT or LOOP may be used at any point within
the DO WHILE . . . ENDDO command. EXIT causes the program
to proceed with the next line following ENDDO. LOOP causes the
program to return immediately to the DO WHILE statement and to
evaluate the logical condition there to determine whether or not to go
through the loop again.
EDIT
[NOAPPEND]
[NOCLEAR]
[NODELETE]
[NOEDIT]
[NOFOLLOW]
[NOMENU]
APP. C
EXIT
This command can only be used within a DO WHILE loop, a FOR
loop or a SCAN WHILE loop. It makes the program continue by exe¬
cuting the code that immediately follows ENDDO, ENDFOR or
ENDSCAN.
FOR <memvar> = < num expl > TO < num exp2 >
ENDFOR
ESSENTIAL COMMANDS AND FUNCTIONS 585
APP. C
GO \GOTO
[RECORD] Knumexpy \
TOP |
BOTTOM |
[IN <alias>]
This command lets you move the pointer within a database hie.
If it is used with a record number, it moves the pointer to that
record; the word RECORD is optional before the number.
If it is used with TOP or BOTTOM, it moves the pointer to the first
or last record of the database hie.
By default, this command works on the database hie that is open in
the current work area, but the optional IN <alias> clause can be used
to specify another work area.
HELP
This command displays the FoxPro Help window, which lets you
look up FoxPro commands and functions. For more information on
FoxPro help, see Chapter 1.
IF <log exp>
[ELSE
. . . ]
ENDIF
[UNIQUE]
This command creates an index file for the database that is open in
the current work area. The index arranges records in an apparent
order based on the field expression; the actual order of the records in
the database file does not change. The field expression may not use
memo fields.
The index’s name is the file name that is specified. FoxPro as¬
sumes an .IDX extension for the index file, but this default may be
overridden by specifying a name that includes a different extension.
After this command is used, the index that has just been created is
open and sets the order of the records in the file. The index will be
updated automatically if it is open when the database file is modified,
or it may be updated using the REINDEX command.
The optional FOR clause makes the index include only records for
which the logical expression is true. When the file is modified, the
index is updated so that it always includes all the records in the file for
which the logical expression is true.
The optional word UNIQUE will make the index include only the
record with first occurrence of a given value for the field expression
that the index is based on. If this expression has the same value for
more than one record, all but the first will not be included in the index
and will not be accessible when the database file is used with this
index as the main index.
APP. C
[ENVIRONMENT]
[SAMPLE]
This command creates mailing labels for the database file that is
open in the currently selected work area. If CONSOLE has not been
SET OFF, the labels are displayed on the screen. They can also be
sent to the printer or to a text file.
Before this command is used, the label form must have been cre¬
ated and saved in a file. The command CREATE LABEL lets you
design these mailing label forms using the label layout window. The
default extension for these files is .LBX.
An existing form may be specified as Kfile namel > of the com¬
mand (or, if the ? option is used, FoxPro will display a scrollable list
allowing you to choose among available label forms).
The ENVIRONMENT option may be used if the environment was
saved when the label form was created. It automatically uses the same
environment—including, for example, an index file to set the order in
which labels are printed.
By default, labels are produced for all records in the database. A scope
clause makes the command produce labels only for the records that fall
in the specified scope. A FOR or WHILE clause makes the command
produce labels only for the records that meet some logical criterion. See
Chapter 5 for more discussion of how these clauses work.
The optional word SAMPLE makes the command produce a
single label as a sample, so you can test the alignment of the labels in
the printer. FoxPro will ask if you want another sample printed, so
you can do repeated tests until the alignment is right.
The optional TO PRINT or TO FILE <file name> clause lets you
send the labels to the printer or to the text file whose name is
specified.
ESSENTIAL COMMANDS AND FUNCTIONS 589
LIST
[WHILE <logexp2>]
[OFF]
This command searches the database file that is open in the cur¬
rent work area from its beginning, until it finds the first record where
the logical expression following FOR is evaluated as true. The logical
expression can make use of any field of the database file, and the
590 MASTERING FOXPRO
APR C
LOOP
MODIFY COMMAND
MODIFY FILE
[NOWAIT]
This command opens a memo window to let you edit the memo
field of the current record of the database file that is open in the cur¬
rent work area. If a record has more than one memo field, you may
use the optional added memo field names to open more than one
memo window at a time—though all memo fields that are displayed
at one time must be from the same record.
By default, when this command is used in a program, the Memo
window is opened and the program does not continue until the user
closes it. The NOW AIT option continues running the program with¬
out waiting for the user to close the Memo window.
APP. C
This command lets you play back the keystrokes that were saved in
the macro whose name is specified. If it is used in a program, the
macro is not played back until there is an opportunity to use the key¬
strokes as input. If more than one PLAY MACRO command has
been used in a program without there being an opportunity for input
ESSENTIAL COMMANDS AND FUNCTIONS 593
(so that several are waiting to execute), they are used in reverse
order: the last command that was used is the first macro that is
played.
PRIVATE < memvar list > | ALL [LIKE < skeleton >
| EXCEPT < skeleton >]
This command allows you to create memory variables that are
accessible only to the program or procedure where they are defined,
so that more than one program or procedure can have memory vari¬
ables of the same name. PRIVATE may be used only in programs and
has no effect if it is used from the Command window.
If a memory variable is defined as PRIVATE, any memory variables
from other programs or procedures that have the same name are tempo¬
rarily hidden while the program or procedure where they are defined is
executed; after it is done, they become active again.
You can use PRIVATE with a list of all the memory variables that
you want to be private, or use ALL to make all memory variables pri¬
vate. If ALL is followed by LIKE <skeleton>, all variables that
match the skeleton will be private. If ALL is followed by EXCEPT
<skeleton>, all variables that do not match the skeleton will be pri¬
vate. Skeletons may be created using literals and the wild-card
characters, ? and *.
APP. C
QUIT
This command terminates FoxPro and returns the user to the op¬
erating system. It can be used in programs as well as from the Com¬
mand window. To avoid possible loss of data, you should always enter
this command before turning off the computer.
READ
[SAVE]
This command lets the user edit the variables of all active @ . . .
GET commands.
In general @ . . . GET commands remain active until the com-
mand CLEAR, CLEAR GETS, CLEAR ALL, or READ is executed.
II the SAVE option is used, though, the READ command leaves
the @ . . . GET commands active, so they can be used again bv
another READ command.
ESSENTIAL COMMANDS AND FUNCTIONS 595
RECALL
[FOR <logexpl'>\
This command unmarks a record that has been marked for dele¬
tion. In its simplest form, it unmarks only the current record (the
record where the pointer is in the database file open in the current
work area).
If an optional scope, FOR, or WHILE clause is used, all the records
included in the specified scope, or all the records for which the logical
expression following the FOR or WHILE is evaluated as true, are
unmarked. For more information on how these clauses work, see
Chapter 5.
Records can be marked for deletion using the DELETE com¬
mand. See this command for more information.
REINDEX
This command rebuilds all index files that are open in the current
work area. For information on how to open indexes, see the com¬
mand USE in this appendix or see Chapter 4.
This command is necessary only if an index file was not open when
its file was being modified, so that it has not been updated to reflect
changes in the file.
[ADDITIVE]
[FOR <logexpl\
[WHILE <logexp2>]
In its simplest form, this command puts new data in a field of the
record where the pointer is, in the database file that is open in the cur¬
rently selected work area. The current data in the field is replaced
with < expl >.
The command may also be used with additional fields and expres¬
sions to replace the data in all of the fields that are listed.
If an optional scope, FOR, or WHILE clause is used, all the records
included in the specified scope, or all the records for which the logical
expression following the FOR or WHILE is evaluated as true, will have
the specified fields replaced with the specified expressions. For more
information on how these clauses work, see Chapter 5. REPLACE can¬
not be used with one of these options on the key field of the active index:
if it is, the replacement may not occur in all the fields specified.
The ADDITIVE option may be used only with memo fields. If it is
used, the data currently in the memo field remains there, and the
data specified in the expression is added to the end of the memo field.
[ENVIRONMENT]
[NO EJECT]
OFF, the reports are displayed on the screen. They can also be sent to
the printer or to a text file.
Before this command is used, the report form must have been cre¬
ated and saved in a file. The command CREATE REPORT lets you
design these report forms using the report layout window. The
default extension for these files is .FRX.
An existing form may be specified as Kfile namel > of the com¬
mand, or if the ? option is used, FoxPro will display a scrollable list
allowing you to choose among available report forms.
The ENVIRONMENT option may be used if the environment was
saved when the report form was created. It automatically uses the
same environment—including, for example, an index file to set
the order in which reports are printed.
By default, reports are produced for all records in the database. A
scope clause makes the command produce reports only for the
records that fall in the specified scope. A FOR or WHILE clause
makes the command produce reports only for the records that meet
some logical criterion. See Chapter 5 for more discussion of how
these clauses work.
The PLAIN option suppresses the printing of the heading at the top of
each page. The HEADING <charexp> option prints the specified char¬
acter expression as the heading at the top of each page.
The NOEJECT option prevents the printer from ejecting a page
before it prints the report. By default, this command sends a form
feed to the printer before beginning its first page.
The optional TO PRINT or TO FILE <file name> clause lets
you send the reports to the printer or to the text file whose name is
specified.
RETURN
APP. C
SCAN
ENDSCAN
Used with ON, this command saves screen output in a text file.
Used with OFF, it stops sending screen output to the text file.
Before this command is used, the text file must be designated using
the command SET ALTERNATE TO <file name^.
The default value setting is OFF, so after the file is designated, SET
ALTERNATE ON must be entered before output is sent to it.
SET AL TERNA TE TO
SET BELL TO
This command lets you change the pitch and duration of the beep
that occurs during data entry.
The number that designates the frequency can be between 19 and
10,000 hertz. The number that controls how long the beep lasts may
be between 1 and 19.
Used without these optional numbers, the command returns the
beep to the default settings, which are 512 hertz and a duration of 2.
Used with ON, this command carries forward the data that is
entered in each record while you are appending data, so that it
appears as the default entry in the next record. Used with OFF, it dis¬
ables this feature.
This command is useful if you must do repetitive data entry.
The default setting for CARRY is OFF.
SET CARRY TO
Used with a field list, this command determines what fields will be
earned forward when SET CARRY ON is used. Only the listed fields
will appear in the next record as default entries.
ESSENTIAL COMMANDS AND FUNCTIONS SO 1
The ADDITIVE option adds the fields that are listed to the fields
listed in a previous SET CARRY TO command that is still active.
Without this option, only the fields listed in the most recent SET
CARRY TO command are carried forward.
Used without a field list, this command returns to the default set¬
ting, in which all fields are carried forward if a SET CARRY ON is
entered.
APP. C
This setting does not affect the commands INDEX and RE¬
INDEX, which always act on all records, regardless of whether they
are marked for deletion.
EXACT is ON, then there will only be a match if the strings are the
same length and have the same characters. If EXACT is OFF, there
can be a match as long as all characters are identical up to the point
where one string comes to an end.
The default setting is OFF.
SET FIELDS TO
If this command is used with a field list, only the fields that are
listed will be accessible to the user or to other commands. For
example, if the user opens a Browse/Change window, it will only
include these fields.
When it is used with a field list, this command is additive. If it is
used a second time, the fields that are listed are added to the fields
that are already accessible because they were listed in the first SET
FIELDS TO command.
When it is used with ALL, the command makes all fields accessible
once again.
Using SET FIELDS TO without a field list or ALL cancels the
fields that have been listed by earlier uses of this command, so a new
SET FIELDS TO <fieldlist> can then be used without being additive.
The command SET FIELDS OFF temporarily disables the restric¬
tions imposed by this command, and the command SET FIELDS ON
enables them again. When SET FIELDS TO is executed, FIELDS
also are automatically set ON.
604 MASTERING FOXPRO
APP. C
SET FILTER TO
SET FORMAT TO
This command lets you use a format file, so that the format in this
hie will be used rather than the ordinary Browse/Change window
when the command APPEND, BROWSE, CHANGE, EDIT, or
INSERT is used.
A format hie consists of @ . . . SAY . . . GET statements that
determine how the screen is arranged. The program hie has an
.FMT extension, and the compiled hie is given a .PRX extension.
SET FORMAT TO may be used with the name of the format hie
that will be used or with the ? option, which makes FoxPro display a
dialog box that lets you choose from a scrollable list of available for¬
mat hies.
If SET FORMAT TO is used alone, a format hie used previously is
deactivated, and FoxPro uses the ordinary Browse/Change window
again.
SET INDEX TO
If you use the ? option, FoxPro displays a dialog box that lets you
choose from a scrollable list of available index files.
If SET INDEX TO is used alone, any indexes that are open in the
current work area are closed.
SET ORDER TO
This command can be used to change the index which is the mas¬
ter index that determines the order of the records if a database file is
in use with a number of indexes active.
The numerical expression refers to the order that the indexes were
in when they were first opened with a USE command or a SET
INDEX TO command. The first index listed in any of these com¬
mands is made the master index. But the SET ORDER TO command
changes the index whose position in the list is specified by the numeri¬
cal expression into the master index instead.
If SET ORDER is used with no numeric expression or with the
number 0, the indexes remain open but none sets the order of
the records. The records are displayed in the actual order in which
they appear in the hie.
[<file>]
When it is used with a file name, this command activates the pro¬
cedure hie that is specified, so that procedures and user defined
funtions in it may be used. If the hie name does not include an exten
sion, FoxPro assumes the extension .PRG.
If you use this command without a hie name, this command closes
an open procedure hie.
SET RELATION TO
This command lets you relate two hies, and its most important use
is in creating relational databases.
To create a relational database, Kexpl > must be a held expression
based on the database hie that is open in the currently selected work
area. <Alias> must refer to an indexed hie that is open in another
work area; it must refer to it either by its name, by the letter or num¬
ber of its work area, or by an alias that you gave it when you opened
the hie. When the command is used in this way, FoxPro looks for the
record in the second hie whose index key expression matches
Kexpiy: as you move the pointer in the hrst hie, it automatically
moves the pointer to the corresponding held in the second hie. Thus,
you can set up a database based on a one-to-one or one-to-many rela¬
tionship between two hies.
lhis command can also be used with an unindexed <alias> hie.
In this case, Kexpl > must be a numeric expression. As you move the
pointer through this hie, the pointer automatically moves to the
record in the alias hie whose record number is equal to the value of
this expression. For example, this version of the command can be
used with the function RECNOQ as Kexpl >, so that the pointer will
move to the record in the alias hie that has the same record number as
the current record in the hrst hie.
ESSENTIAL COMMANDS AND FUNCTIONS 60 7
This command opens and closes the View window, to let you set
up a working environment. Entering SET VIEW ON is equivalent to
selecting View from the Window menu; entering SET VIEW OFF is
equivalent to closing the window by pressing Esc or clicking the close
box. For more information on views, see Chapter 7.
This command lets you use a working environment (or View) that
you have previously saved in a .VUE file. You may specify the file
name or use the ? option to select it from a scrollable list of available
•VFJE files. For more information on views, see Chapter 7.
SKIP
In its simplest form, this command sorts the hie that is open in the
current work area, based on the held that is specihed, and in ascend¬
ing order. It also puts the result in the hie that is specihed.
The option [/A] lets you specify ascending order explicitly, though
it is done by default if it is not specihed. The option [/D] lets you sort
in descending order. The option [/C] makes the sort ignore the case of
a character held; if it is not included, the sort will be in ASCII order,
with uppercase before lowercase letters.
If you specify more than one held to sort on, subsequent helds will
be used as tie-breakers, in case the values in the hrst held are identi¬
cal. You can use the [/A], [/C], or [/D] options separately for any of
the helds.
The ASCENDING and DESCENDING options apply only to helds
that do not include the [/A] or [/D] options, and determine whether
these helds will be sorted in ascending or descending order.
By default, all the records in the currently open hie are sorted into
a new hie. If a scope clause is used, only the records that fall in the
specihed scope are sorted into the new hie. If a FOR or WHILE clause
is used, only the records that meet some logical criterion are sorted
610 MASTERING FOXPRO
APP. C
into the new file. If a FIELDS clause is used, only the fields that are
listed are included m the new file. See Chapter 5 for more discussion
of how these clauses work.
The SORT command, in addition to creating a new output file,
uses temporary work files, and so it uses up to three times as much
disk space as the space occupied by the original file. If this disk space
is not available, FoxPro can terminate abnormally, causing a possible
loss of data.
SUM
[WHILE <logexp2>]
In its simplest form, this command adds the values in all numeric
fields of all records in the database file that is open in the currently
selected work area. If the command SET TALK OFF has not been
used, the total for each field is displayed as FoxPro “talk.”
The option TO Kmemvar list> \ TO ARRAY <array rmme> lets you
store the results in memory variables. FoxPro creates the memory vari¬
ables specified, if they do not already exist. The array must be declared
with the DIMENSION or DECLARE command before using this com¬
mand. The order in which values are assigned to the memory variable
ESSENTIAL COMMANDS AND FUNCTIONS 611
list or to the elements in the array depends on the order in which the
numeric fields appear in the database.
By default, all the records in the currently open file are added. If a
scope clause is used, only the records that fall in the specified scope are
added. If a FOR or WHILE clause is used, only the records that meet
some logical criterion are added.
TEXT
ENDTEXT
This command lets you create a new database file that contains
totals of the numeric fields of the database that is open in the cur¬
rently active work area.
By default, the totals are given for all records that have the same
value in the key field that is specified. For example, if you total on
STATE (assuming there is a STATE field in the database), the new
file you create will have a record for each state in the original file, and
that record will include the totals of all the numeric fields in the origi¬
nal file’s records from that state.
For this command to work properly, the file must be sorted on the
key field or must be indexed on the key field and in use with that
612 MASTERING FOXPRO
APP. C
index as the major index that determines the order of the records.
If a scope clause is used, only the records that fall in the specified
scope are included in the totals. If a FOR or WHILE clause is used,
only the records that meet some logical criterion are included in the
totals.
TYPE <filel>
USE
In its basic form, this command opens the specihed database hie in
the current work area; if a hie is open in the work area already, that
hie is closed.
If it is used with a ? instead of with a hie name, this command dis¬
plays a scrollable list to let the user choose an available database hie.
The command USE by itself simply closes any database hie that is
already open in the current work area without opening a new one.
ESSENTIAL COMMANDS AND FUNCTIONS 613
The option IN < work area > opens the database hie in the work
area that is specified instead of in the current work area.
The option INDEX <indexfile list> opens the specified index hies
as well as the database hie. These index hies must have been created
previously. The hrst index hie in the list is the main index, which sets
the order of the records, and all index hies in the list are updated to
f
WAIT
ZAP
This command removes all records from a database, leaving only
the database structure; this data cannot be recovered. It is equivalent
to entering the command DELETE ALL and then the command
PACK, except that it works more quickly. If SAFETY is SET OFF, it
will not warn you before deleting all your data permanently.
Needless to say, it should be used with great caution—if at all.
614 MASTERING FOXPRO
APP. C
FUNCTIONS
This function returns .T. if the value of expl falls between the
values of exp2 and exp3—or, more precisely, if expl is greater than or
equal to exp2 and expl is less than or equal to exp3. Otherwise, it
returns .F.
DATEQ
This function returns the current system date—the date on your
computer’s clock/calendar or the date that you entered when you
started your computer.
APP. C
LOWER(<char exp>)
This function returns the specified character expression with all its let¬
ters converted to lowercase. It does not affect non-alphabetic characters.
272-273
BROWSE LAST command, 94, 110, 565
backup copies, 283 Browse menu, 13, 79, 92, 94-99, 119
attribute for, 534 Goto option, 99
automatic during structure modification, 592 Grid On option, 96
backslash (\) symbol, for root directory, 58 Seek option, 99
Backspace, 25 Toggle Delete option, 99
Browse window, 78, 79, 269 converting to upper or lower case, 127
vs. closing windows, 90 .DBF file name extensions, 44, 50, 71, 82, 342
editing, 12 debugging, 15, 381, 387, 388, 390, 607. See also Trace
I
G
IBMBIO.COM file, 535
Gen menu (FoxView), 348-349, 368 IBMDOS.COM file, 535
GET command, 394, 433 .IDX file name extensions, 121, 587
global variables, 594 IF command, 377, 586
GO BOTTOM command, 445 IF ELSE ladder, 411-412
GO command, 586 IF . . . ELSE . . . ENDIF command, 408-410, 448
GOTO command, 105, 380, 586 combined with DO loop, 409
Goto Line (Edit menu), 308 IF .NOT. EOF() STATEMENT, 491
Goto option, 99, 103 IIF() (immediate if) function, 616
Grid On] Off option, 96, 99 IMPORT, in FoxView, 342-343
group bands, 238 Import Format, in FoxView, 348
group footer, 239 importing data, 314-316
group header, as page header, 222 included-in operator ($), 190
Group text button, 222 indentation in program code, 383, 450
grouped data for DO WHILE loop, 402
calculations for each, 232 of nested loops, 406
with header and footer, 216 INDEX ON command, 587
grouping macros in sets, 303 Index On dialog box, 117
groups of files, tagging, 526 INDEX option, in USE command, 613
Index radio button, 236
indexes, 173-176
H
advantages of, 116
hard disk, FoxPro space needs on, 514 alphabetizing by name, 141-148
headers changing, 605
for data group, 221 creating, 114, 236, 587
for pages, 237 for data groupings, 223
in report layout window, 216 in descending order, 149-150
Heading option, for printing, 215 expressions in, 141-150
help file name for, 117
adding on-screen, 362 on key field, 265
for FoxView, 337, 355 listing, 343
installing files for, 517 main, 174, 182, 425, 427, 605
specifying file for, 287 maintaining, 150-156
HELP command, 586 maintaining multiple, 115
Help window, 34-37 for multi-record queries, 185-187
for commands using scope clause, 200 opening, 144-145, 604-605
for functions, 148 opening multiple, 150-151
in Shell, 337 overwriting, 147
hidden files, 535 programming analysis and, 423, 425
hidden windows, 22 queries using, 162, 181-183
Hide All option (Window menu), 23 query built into, 169, 196-199
Hide option (Window menu), 16 rebuilding, 595
630 MASTERING FOXPRO
loops, 377, 381, 401-407, 582. See also infinite loop main menu, 7
delaying, 404 in application generation, 429-433
DO WHILE, 494 in structure diagram, 425
DO WHILE .T., 490 main module of program, 475
LOWEF.() function, 127, 617 Make Backup (Preferences dialog box), 313
lowercase characters, converting, 127 many-to-many relationship, 262
Lowest, of field values, 232 MAP
LTRIMQ function, 129, 140, 239, 617 in Fox View, 343
in IMPORT, 343
MAP Datafile, in Fox View, 347
M margins
machine language, 379 left and right, 220
macro substitution function, 614 and printed lines per page, 218
macros, 297-304 top and bottom, 220
clearing, 304 master index, 605. See also main index
creating, 294, 298-303 Match Words check box, in Find, 529
current vs. saved, 303-304 Math menu, in expression dialog box, 124
default settings for, 298 MAX() function, 323, 567
grouping in sets, 303 MD (Make directory), 59, 341
maximum keystrokes in, 297 memo data type, 49
saving, 294 memo fields, 81
mail-merge, exporting for, 464-466 changing, 76
Mail Power! program data entry to, 86-87
data exporting module for, 465-466 editing, 92
data submenu for, 437-450 inability to sort on, 156
database file structure for, 435 as separate file, 50
GETDATA procedure for, 489-490 substring search in, 190
label menu for, 459-464 width of, 55
LOOKUP module for, 445-450 memo window
main menu, 431-432 closing and saving, 81
preliminary testing of, 444 opening for edit, 591
report menu for, 451-459 memory variables, 349, 385, 492
screen format for, 442 calculations with, 295, 318-325
SCRNHEAD, 478-480 creating, 562
structured form of, 502-511 in dBASE III, 477
mailing label program. See also Mail Power! program in expressions, 123
mailing labels, 211, 243-251, 421. See also label forms and FOR command, 585
avoiding blank lines in, 247 private, 593
creating, 588 public, 594
default settings for, 250 STORE command and, 610
deleting blanks from, 129 for user input, 387, 483-492
field expressions in, 211 memory, of calculator, 546
programming for, 450-464 menu bar, 7
using related files, 281 color for, 328
mailing list application, creating, 422-466 moving to, 9
main index, 427, 605 Report menu pad in, 213
determining, 425 menu-driven applications, creating, 367
and Seek, 182 menu structure, 6-17
WHILE clause to search with, 174 menu style, 368
632 MASTERING FOXPRO
display during running, 471, 498 logical expressions in, 165-173, 190
Save As option (File menu), 11-12 screen output, saving to text file, 599
,pA / nv*'**
0 600 oO 'Jd . 6 J O 3 J 0 0(3
Q3 £p 0C&7 &A 02 0006 $ro£df & ! \ 0*°* c,t)d0A
___ .^_o$4%\0foc> 60 0 0
Af 00 oo 6 6 A rypo
A
Ur OtELV S/zr'i f f£
$\l£ Of
f\£u?
!* /)
4/(j 7" 4- yf?/^ /^/LE
%r rw<r
FSF JO/ES
i/j'f s
TW£ $TP.OCfVR<£r IAStPPPr ****** ~
Tfc- ftyup siwasi f/Wtt <70,08 PROMPT fPElP s/Z£ T'TIE ’fesr>
ACTIVATE PcofOE Etecaj
Pr wr
AL-! 7p /pi (a ->/kc ) To /H-LT/SfAA {_ j
/r Mt-tr ytetp \
a-> Azt oar s r ~ S, f- TJoil
NAME COMPANY
STREET CITY
STATE ZIP
ORDER FORM (There is no obligation to order) SHIPPING AND HANDLING PLEASE ADD $2.00
PER BOOK VIA UPS
PLEASE SEND ME THE FOLLOWING: FOR OVERSEAS SURFACE ADD $5.25 PER
BOOK PLUS $4.40 REGISTRATION FEE
TITLE: QTY PRICE FOR OVERSEAS AIRMAIL ADD $18.25 PER
BOOK PLUS $4.40 REGISTRATION FEE
___ _ CALIFORNIA RESIDENTS PLEASE ADD
APPLICABLE SALES TAX
---- -- - TOTAL AMOUNT PAYABLE
_ _ _ □ CHECK ENCLOSED □ VISA
□ MASTERCARD □ AMERICAN EXPRESS
-—---- - - ACCOUNT NUMBER _
CUSTOMER SIGNATURE
CHECK AREA OF COMPUTER INTEREST: OTHER COMPUTER TITLES YOU WOULD LIKE
□ BUSINESS SOFTWARE
TO SEE IN PRINT:
□ TECHNICAL PROGRAMMING
□ OTHER:__
□ COMPREHENSIVENESS □ ENGINEER/TECHNICAL
□ NEW TO COMPUTERS
PACKAGE:
NAME ______
PACKAGES
□ PROFESSIONAL PROGRAMMER
SYBEX, INC.
2021 CHALLENGER DR. #100
ALAMEDA, CALIFORNIA USA
94501
SYBEX
SEAL
SYBEX Computer Books
are different.
Here is why . . .
At SYBEX, each book is designed with you in mind. Every manuscript is
carefully selected and supervised by our editors, who are themselves
computer experts. We publish the best authors, whose technical expertise
is matched by an ability to write clearly and to communicate effectively.
Programs are thoroughly tested for accuracy by our technical staff. Our
computerized production department goes to great lengths to make
sure that each book is well-designed.
Setting Up the
Current Work Area
The Setup dialog box lets you control the database file that is open in the cur¬
rently active work area. You can change the actual structure of the database,
and you can create, open, or modify indexes to control the order in which the
database, fields, and records are used. You can also define the format used for
editing and appending.
Database: EMPLIST
The Setup Structure: <ModifQ> Indexes: Index
dialog box
►FNAME C 15 0 •DATES |< Add. . . >1
LNAME C 20 0 NAMES <Modify...>
ADDRESS C 25 0 WAGES < Remove >
APT NO C 5 0 ZIPS <Set Order>
Creating a View
The View window lets you create an entire working environment. You can
open and set up multiple databases at the same time, and you can set relations
among them to create relational databases. You cam also control simpler environ¬
ment variables. All these settings can be saved in a .VUE hie, and the entire
view can be used again simply by opening that hie.
View
The View ►< View > Work Areas < Relations >
window
<0n/0ff> ►WAGES
1—^ENPLIST
<Files >
<Setup >
FoxPro
Mastering FoxPro is a highly readable hands-on introduction to
database management, using the dBASE-compatible FoxPro system.
Perfect for beginning and intermediate users who want to build on a
solid base of skills, it covers everything from exploring the software’s
menus for the first time to creating full-featured custom database
applications.
Master the concepts of relational database management by learning with FastTmck Speed Notes
specific techniques for working with multiple database files. A realistic
employee recordkeeping system serves as a hands-on example.
in-depth tutorial, suitable for first-time programmers, shows exactly not just information.
how to plan, develop, test and debug a sophisticated custom FoxPro
application, using modular programming techniques.