===============================================================================
                                README.TXT
                    For the dUFLP LIBRARY Files (attached)
               (dUFLP = dBASE User's Function Library Project)
                               Version 1.92
                                 12/07/92
===============================================================================
This library system is freeware (no charge). This file (README.TXT) is a small 
amount of description for the attached procedure file. I have spent many hours 
compiling functions and procedures that I have found useful. Some of these (a 
few) are ones I have written myself, many are ones I have incorporated here
from a variety of sources, usually the Borland (once Ashton-Tate) Bulletin
Board (BORBBS). There were a lot of good people using this board, both as 
sysops/sigops, and as users, and I have learned alot about dBASE IV Programming 
from these people. 

This is my attempt at returning the favor. 

All procedures/functions in PROC and accompanying files are public domain. 
I ask that if you use them (or in this PROC file) with your systems,
that you include ALL the documentation, including (ESPECIALLY) the name of 
the programmer (Credit should go where it's due, after all). 

SPECIAL THANKS: To Jay Parsons (CIS: 70160,340), who has done 1) a LOT of the 
routines you will find here, and 2) a lot of work with me to ensure that
there is integrity and consistency in this system.

Take a look wherever you download this for:
dHUNG2.ZIP   -- a file containing the description of the dBASE User's Function
                Library Project standards (dUFLP) which are used in these 
                programs.

This is a set of dynamic files -- they're always changing. Please feel free to 
send me comments and/or suggestions on ways to better it (which includes both 
functions and procedures, and suggestions to make the ones here better). I can 
be reached on Electronic Services: 

USSBBS: KenMayer  
CompuServe: 71043,3232

or at home at:

   Ken Mayer
   2308 Alva Avenue
   El Cerrito, CA 94530
   (510) 215-5879 (Home)

==========
DISCLAIMER
==========
No guarantees are given. Last attempted, all these routines worked. I take no
responsibility for their use, particularly if something happens to your data.

========
PROBLEMS
========
Problems with individual procedures and functions should be addressed, if 
possible, to the author (note the 'Programmer' listed in the first line of
the internal documentation for each routine). If you cannot reach them, contact
me at my id on the BBS, and I will see what I can do.

============
INSTRUCTIONS
============
---------------------------
dBASE IV, version 1.5 users
---------------------------
In order to use these, you need to understand (and this is brief) how dBASE IV,
version 1.5 uses functions and libraries. Basically, it follows a 'search path'
based on your programs and files, as well as its own internal functions.
dBASE starts at the top of the following list, and if it cannot find the 
function or procedure named in your program, it goes to the next item in the 
list until it either finds it, or doesn't find it, as the case may be. If not,
you will get the dBASE error message about not finding a function.

1)  dBASE INTERNAL FUNCTIONS AND COMMANDS
2)  SYSPROC = "System Procedure Filename" (set in CONFIG.DB)
3)  Current Program (the one executing at that time)
4)  SET PROCEDURE TO <proc name>
5)  Calling Program (a main menu program, for example)
6)  SET LIBRARY TO <library name>

To use these files in dBASE IV, version 1.5, you should something along
the following lines as a layout: 

   For any procedures/functions that are required specifically for your
   system, and no other, place those in your own procedure file, and
   refer to that in the SYSPROC command in your CONFIG.DB file. Example:

   SYSPROC = MYPROC

   To use the 'standard' library file for this system, in your main program 
   (by 'main program' we could be discussing a MENU program, or other front-
   end program) put the command:

   SET PROCEDURE TO PROC  && or point to the appropriate directory
   
   And in the appropriate programs, or where needed,

   SET LIBRARY TO <library file> && based on those below

This is just one method of handling this. One thing that can make life easier,
if you switch LIBRARY files a lot, is the dBASE IV, 1.5 option to the SET
command:  SET("LIBRARY"). This can be used in the following manner:

    cLibrary = set("LIBRARY")  && save current library name
    set library to NEWLIB      && set new one
    *-- do function/procedure calls from new library
    set library to &cLibrary   && return to previous library file

     OR you could use the new function SwitchLib():

    cOldLib = switchlib("FILES")
    *-- execute function/procedure
    cOldLib = switchlib("&cOldLib")

SUGGESTION: If you store your copy of the LIBRARY files (and PROC) in another
directory on the drive, you might want to define a public memvar called
something like:  c_LibPath and store the path in in. This way you can
use that with your routines to call the libraries. Something along the following
could be useful:

PUBLIC c_LibPath
Store "C:\DBFILES\PROC\" to c_LibPath
  *-- processing
cOldLib = SwitchLib("&c_LibPath.FILES")  && send with path, as well as filename
*-- execute function/procedure
cOldLib = SwitchLib("&cOldLib")          && should return path

This will make it easier to update if you are setting this up for a client --
you can change the c_LibPath variable in the setup or menu program ONCE, and
not have to worry about it again.

NOTE: that in some of the library files there are functions which require 
the use of functions in OTHER files (i.e., some functions in NAVIGATE use 
some functions that are in TRIG). I have attempted to ensure that I have copied
INTO those library files the appropriate functions, so you don't spend too much
time tearing your hair out.

-------------------
dBASE IV, 1.1 Users
-------------------
To use these procedure files in their entirety, use the DOS Copy command to 
concatenate the library files to the PROC file. Something along the following
lines (although you should check to make sure you have all the files):

COPY PROC.PRG+SCREEN.PRG+COLOR.PRG+TRIG.PRG+CONVERT.PRG+ <etc.>

You should note that in some of the library files, there are duplicated 
functions used, due to the fact that some users in 1.5 might wish to only use
one or two of the library files. You can also use just the individual library
files in your SET PROCEDURE command, if you wish. 

Add to your programs (a menu or startup routine is one of the best places) 
the line:

SET PROCEDURE TO PROC

To use individual routines, rather than the whole library, extract them using 
your favorite ASCII editor, or remove the routines from this file (you might 
want to copy it first) that you do not feel you will need.

================================================================================
WHAT'S HERE?
================================================================================

Some of the places routines are placed may seem a bit arbitrary -- they are. 
These decisions were made based on the functions/procedures I use the most in 
my own routines. Since the original purpose of this library was my own use, 
I felt it my prerogative to be the one to make the final decision as to what 
routines were left in PROC.PRG, and which got moved to the LIBRARY files. 

Included in this LIBRARY System are the following files:

Text Files
README.TXT   -- You're looking at it.
WHATS.NEW    -- This is a description of the new features for this system.
CONTRIB.TXT  -- How to contribute to the Library Project.
JPMOUSE.TXT  -- An explanation from Jay on the JPMOUSE.BIN file, attached
                (with his permission). See also the function ISMOUSE() and
                procedure file SETMOUSE in PROC.PRG.
DISK.TXT     -- A very brief discussion on the use of DISK.BIN.
SEARCH.TXT   -- A very brief discussion on the use of SEARCH.BIN.
USERID.TXT   -- A very brief discussion on the use of USERID.BIN.
PRINTSCR.TXT -- Discussion on the use of PRINTSCR.BIN
SCREEN.TXT   -- Discussion on the use of SCREEN.BIN

Procedure and Library Files -- Described Below
ARRAY.PRG
COLOR.PRG
CONVERT.PRG
DATES.PRG
ERRLOG.PRG
FIELDS.PRG
FILES.PRG
FINANCE.PRG
FRPG.PRG
MEASURE.PRG
MISC.PRG
NAVIGATE.PRG
OBSOLETE.PRG
PICKLIST.PRG
PROC.PRG
SCA.PRG
SCREEN.PRG
STATS.PRG
STRINGS.PRG
TIME.PRG
TRIG.PRG
WINDOWS.PRG

BIN Files -- used in routines attached.
JPMOUSE.BIN
DISK.BIN
PRINTSCR.BIN
SCREEN.BIN
SEARCH.BIN
USERID.BIN
OX.SYS

Below is a quick list of all the procedures and functions included in the 
library files in the sequence they are presented in the programs themselves:

===================================
PROC.PRG -- The MAIN PROCEDURE File
===================================

----------------------------------
MESSAGE/SCREEN PROCESSING ROUTINES
----------------------------------
PrintErr    -- used to display a "standard" error message for printer 
               errors (is it on, online, out of paper?).
               Usage: do PrintErr
Open_Screen -- Used to add texture to the background for an opening screen or
               menu.
               Usage: do Open_Screen
JazClear    -- performs a nice center to edge of screen clear (using a box) ...
               Usage: do JazClear
Wipe        -- performs a left-to-right wipe of a window. Nice effect.
               Usage: do Wipe with <nULRow>,<nULCol>,<nBRRow>,<nBRCol>
Center      -- used to center text anywhere on the screen (optional colors).
               Usage: do Center with <nRow>,<nWidth>,"<cColors>","<cText>"
Surround()  -- Used to display text at X,Y position, surrounded with a double-
               line box.
               Usage: Surround(<nRow>,<nCol>,"<cColor>","<cText>")
Message1()  -- Displays a single-line message, waits for user to press a key
               before program moves on.
               Usage: Message1(<nRow>,<nWidth>,"<cColor>","<cText>")
Message2()  -- Same as above, but displays message in a window (with shadow).
               Usage: Message2("<cText>","<cColor>")
Message3()  -- Same as above, but will handle LONG messages, wrapping inside
               window.
               Usage: Message3("<cText>","<cColor>")
Message4()  -- 2-Line message in a window, pauses for user.
               Usage: Message4("<cText1>","<cText2>","<cColor>")
ProgBar     -- Monitor program activity, so user does not get worried that
               the machine went into limbo. A graphic version of what the
               "MONITOR" procedure in PROC.PRG does.
               Usage: Do ProgBar with <nQuan>,"<cWindCol>","<cFillCol1>",;
                                 "<cFillCol2>","<cMessage>",<nWindWidth>
ScrnHead()  -- Used to display a screen header inside a box (with a shadow).
               Usage: ScrnHead("<cColor>","<cText>")
YesNo()     -- Used to ask a "yes/no" type question, allows three lines of 
               message, and uses menu pads to choose (move cursor, press 
               <enter>).
               Usage: YesNo(<lAnswer>,"<cMess1>","<cMess2>","<cMess3>",;
                             "<cColors>")
YesNo2()    -- As above, but allows programmer to choose position on screen.
               Usage: YesNo2(<lAnswer>,"<cWhere>","<cMess1>","<cMess2>",;
                           "<cMess3>","<cColors>")
                   where cWhere may be one of the following:
                         UL = Upper Left
                         UC = Upper Center
                         UR = Upper Right
                         CL = Center Left
                         CC = Center Center
                         CR = Center Right
                         BL = Bottom Left
                         BC = Bottom Center
                         BR = Bottom Right
                   Anything else will default to CC.
ErrorMsg()  -- Allows 2 lines of message, first is ** ERROR **, or optionally,
               ** ERROR # **  where '#' is a number (if "<cErr>" is empty,
               (""), system uses first option, but there must be SOMETHING
               there). 
               Usage: ErrorMsg("<cErr>","<cMess1>","<cMess2>","<cColors>")
Alert2()    -- Brings up an "Alert" dialog box (similar to Windows).
               Usage: Alert2("<cTitle>","<cMessage>","<cColor>"[,"<cBorder>"])
Shadow      -- Used for windows/boxes to display a shadow, giving 3-D effect.
               Usage: do Shadow with <nULRow>,<nULCol>,<nBRRow>,<nBRCol>
VPick()     -- Multiple-item Picklist -- this routine will allow you to create
               a simple vertical picklist of items, returning the first letter 
               of the option selected, or a null string if the user pressed 
               <Esc>.
               Usage: VPick(<nRow>,<nCol>,"<~Option1~Option2~Option3>",;
                             "<cTitle>","<cMessage>",<lShadow>,<cColor>)
HPick()     -- Very much like VPICK() above, but does a Horizontal Picklist.
               Usage: HPick(<nRow>,<nCol>,"<~Option1~Option2~Option3>",;
                             "<cTitle>","<cMessage>",<lShadow>,<cColor>)

-------------------------
COLOR PROCESSING ROUTINES
-------------------------
SetColor    -- Sets colors to contents of a memvar to handle various parts of
               the screen. THIS IS A NEW ROUTINE -- USERS OF THE OLD 
               SETCOLOR and SETCOLOR2 ROUTINES SHOULD CHECK "OBSOLETE.PRG".
               Usage: do SetColor with <cColorVar>
ReColor     -- Restores colors to those held in a string of the form returned
               by SET("ATTRIBUTE").
               Usage: Do ReColor with <cColors>
ColorBrk()  -- Returns one of three portions of a color variable as used in
               many of my own routines (YESNO, etc.). Used for explicitly
               setting colors.
               Usage: ColorBrk(<cColorVar>,<nField>)
FBClrBrk()  -- Returns either the foreground or the background (FB) of a
               color memory variable or string.
               Usage: FBClrBrk(<cColorVar>,<cType>)

----------------------------
STRING MANIPULATION ROUTINES
----------------------------
AllTrim()   -- Trims both sides of a character field/memvar.
               Usage: AllTrim(<cString>)
Justify()   -- This is copied here for use in other routines from STRINGS.PRG.
State()     -- This is used for validation of a STATE (two letter) code ... 
               (returns .t. or .f.) -- useful for data entry.
               Usage: State(<cState>)

----------------------
DATE HANDLING ROUTINES
----------------------
DateText()  -- Convert date to Month Day, Year format.
               Usage: DateText(<dDate>)
DateText2() -- As above, adds day of week (DoW, Month Day, Year).
               Usage: DateText2(<dDate>)
Age()       -- Returns the age of someone as of DATE(), given their birthdate.
               Usage: Age(<dDate>)

-----------------------
FIELD HANDLING ROUTINES
-----------------------
IsUnique()  -- Used to check a keyfield in a database to see if it's unique.
               Usage: IsUnique(<xValue>,<cOrder>)

--------------
MISC. ROUTINES
--------------
SetPrint    -- Used to setup the printer memory variables for a print job.
               Usage: do SetPrint
DosRun()    -- Used to execute a DOS command/program from inside dBASE, handles
               windows and such by restoring them when done.
               Usage: DosRun(<cCmd>)
ScrnRpt()   -- Shows a dBASE Report on screen, and pauses when the screen is
               full.
               Usage: ScrnRpt(<cRpt>)
SwitchLib() -- Changes the current library file to another. Useful when doing
               quick changes to execute a function/file in another library.
               Usage: SwitchLib(<cNewLib>)
IsMouse()   -- Looks at system for a mouse driver, if there, it turns off
               the mouse. Uses JPMOUSE.BIN.
               Usage: IsMouse()
SetMouse    -- Used to toggle a mouse, requires JPMOUSE.BIN and a public
               memvar c_Mouse set to the most current state ("OFF" means
               the mouse is "OFF" ... and will be toggled ON in the next
               call to SetMouse).
               Usage: On Key label ... DO SetMouse
VerLevel()  -- Used to return numeric value of current version of dBASE or
               RUNTIME. Useful with those version specific routines.
               Usage: VerLevel()

=============
LIBRARY FILES
=============

The following files are the 'library' files that contain all routines in this
system not contained in PROC.PRG. See the section of this document marked
'INSTRUCTIONS' for how to use these. Please notice that some functions which
are used in specific LIBRARY files (such as NAVIGATE.PRG, which uses some of
the functions in TRIG.PRG) are duplicated in some of the other library files.
This was done to make life easier on the programmer. Since dBASE IV, 1.5 does
not allow multiple library files (although one can hope for such a feature in
future editions), we are stuck having to duplicate some routines.

--------------------------------------------------------------------------------
SCREEN.PRG -- Screen Handling
--------------------------------------------------------------------------------
Radio()     -- This routine creates a "radio-button" routine. You can have
               up to four options. Returns # of item chosen ...
               Usage: Radio(<nULRow>,<nULCol>,<nChoice>,"<cTxt1>","<cTxt2>",;
                             "<cTxt3>","<cTxt4>","<cTitle>","<cColor>")
CheckBox    -- This routine does a "CheckBox" much like Windows/Mac type
               software, with up to four options. NOTE -- the items marked
               in the format must be a) logical, and b) fields/memvars.
               They cannot be literal values, due to limitations of dBASE
               parameter handling.
               Usage: Do CheckBox with <nULRow>,<nULCol>,<lChk1>,<lChk2>,;
                                        <lChk3>,<lChk4>,"<cTxt1>",;
                                        "<cTxt2>","<cTxt3>","<cTxt4>",;
                                        "<cTxt0>","<cColor>"
MenuPad()   -- Used to define menu pad and popup bars as a specific length.
               Function will truncate if longer than needed, and will
               pad with spaces otherwise.
               Usage: MenuPad("<nChoice>",<nLength>)
Banner()    -- Used to display a scrolling "banner" message on the screen.
               Usage: Banner(<nRow>,<nCol>,<nwidth>,"<cMessage>","<cColor>")
SeeMatch()  -- Displays instant lookup match on a field in a shadowed box.
               Usage: SeeMatch("<cFile>",<cSeekExp>,"<cReturn>",<nULRow>,;
                               <nULCol>,<nBRRow>,<nBRCol>,"<cColor>")
MsgExp()    -- Used to display a message (or an error message), centered on
               the screen. Does not use the "(Press Space)" bits that dBASE
               uses on an error message ... The message and the line on which
               it is displayed will be the same color.
               Usage: MsgExp("<cExp>")
Dialog()    -- Routine to provide a 'standard' set of dialog boxes and buttons
               for all applications. 
               Usage: Dialog("<cMsg>",<nType>,"<cBorder>",<nDefBut>,<lShadow>,;
                             "<cWind>","<cButton>")
               nType is used to describe the dialog box type, options are:
               0:      'OK'
               1: 'OK' 'CANCEL'
               2: 'ABORT'  'RETRY'  'IGNORE'
               3: 'YES'  'NO'   'CANCEL'
               4: 'YES'  'NO'
               5: 'RETRY'   'CANCEL'
YesNoCan()  -- A dialog box, defaults to 'Yes/No/Cancel', varies in size,
               depending on programmer needs, optional row position. Nice
               modification of the YESNO() function in PROC.PRG.
               Usage: YesNoCan("<cAnswer>","<cMess1>","<cMess2>","<cMess3>",;
                               "<cPrompt1>","<cPrompt2>","<cPrompt3>",;
                               <nTopRow>,"<cColor>")
ProgBar2    -- Same as above, but a bit simpler to use.
               Usage: Do ProgBar2 with <nQuan>,"<cWindCol>","<cFillCol2>",;
                                 "<cFillCol2>"
MovePad     -- Moves menu pad on selection of a letter. 
               Usage: Do MenuPad with <cLetter>,<lSelect>,<cChoices>
Monitor     -- Displays a box, showing total records in database -- is designed
               to be used in a system that does a record-by-record update, 
               so the user knows something is happening. You need to add code
               to display actual record numbers as the task is happening.
               Usage: do Monitor with "<cText>","<cColors>"
Monitoroff  -- Cleanup for Monitor procedure above.
               Usage: do MonitorOff

--------------------------------------------------------------------------------
COLOR.PRG -- Color Processing
--------------------------------------------------------------------------------
AttriByte() -- Returns the attribute byte of a dBASE Color code.
               Usage: AttriByte("<cCode>")
ColorName() -- Converts an attribute value for an area to the name of the
               corresponding color combination. 
               Usage: ColorName(<nAttr>)
ColorCode() -- Given a color attribute byte, returns dBASE color code.
               Usage: ColorCode(<nAttr>)
ColorOf()   -- Returns the color of attributes in dBASE, as currently set.
               Usage: ColorOf("<cArea>")

--------------------------------------------------------------------------------
STRINGS.PRG -- Character String Processing
--------------------------------------------------------------------------------
Proper()    -- Converts text to "proper" case (upper/lower case, handles
               contractions, Mc, Mac, etc.). Useful for names (converts first
               letter to upper case, the rest to lower, except as above).
               Usage: Proper("<cArg>")
Justify()   -- Used to justify a field or memvar (or character expression) 
               within a specific field width. 
               Usage: Justify(<cFld>,<nLength>,"<cType>")
                   cType must be L (left), C (center), or R (right)
Dots()      -- Used to pad a field with dots (dot leader, trailer ...) 
               Usage: Dots(<cFld>,<nLength>,"<cType>")
                   cType must be L (left), C (center), or R (right)
CutPaste()  -- Used to Cut a string and Paste another in it's place. It's
               an easier way to use the STUFF() function.
               Usage: CutPaste(<cFld>,<cLookFor>,<cRepWith>)
LastWord()  -- Used to return the last "word" of a string of characters (words
               being bracketed by spaces).
               Usage: LastWord(<cString>)
VStretch()  -- Displays a long character field (254 char) on screen, with
               wrap-around, and handles proper word-breaks - you give
               dimensions for where you want it displayed (window).
               Usage: VStretch(<cFld>,<nULRow>,<nULCol>,<nBRRow>,<nBRCol>)
AtCount()   -- Returns the number of times a string is found in another.
               Usage: AtCount(<cFindStr>,<cBigStr>)
IsAlNum()   -- If first character of string is alphabetic or digit, returns
               .t., otherwise returns .f..
               Usage: IsAlNum(<cChar>)
IsAscii()   -- If first character is in ASCII (normal, not extended) character
               set, returns .t., otherwise returns .f..
               Usage: IsAscii(<cChar>)
IsCntrl()   -- If first character is a delete or control character, returns
               .t., otherwise returns .f..
               Usage: IsCntrl(<cChar>)
IsDigit()   -- If first character is a digit, returns .t..
               Usage: IsDigit(<cChar>)
IsPrint()   -- If first character is a printing character (space through
               chr(126), returns .t..
               Usage: IsPrint(<cChar>)
IsXDigit()  -- If first character is possible hexadecimal digit, returns .t..
               Usage: IsXDigit(<cChar>)
IsSpace()   -- Returns .t. if first character is space, tab, carriage return,
               line feed, vertical tab, or formfeed.
               Usage: IsSpace(<cChar>)
Name2Label()-- Returns a name held in five fields as a single field for the
               purpose of printing in a label.
               Usage: Name2Label(<nLength>,<cPrefix>,<cFirstName>,;
                                  <cMidName>,<cLastName>,<cSuffix>)
StrpBrk()   -- Search string for first occurrence of any specific character(s).
               Usage: StrpBrk(<cCharSet>,<cBigStr>)
RAt()       -- Reverse AT() - returns position of a character string in its  
               last position in a larger string ...
               Usage: RAt(<cFindStr>,<cBigStr>)
StrRev()    -- Reverse a string.
               Usage: StrRev(<cAnyStr>)
Strip2Val() -- Strip characters from the left until reaching one that might
               begin a numeric value ...
               Usage: Strip2Val(<cString>)
StripVal()  -- Strip characters until reaching one that is NOT part of a
               number.
               Usage: StripVal(<cString>)
ParseWord() -- Finds first word in a character string.
               Usage: ParseWord(<cW>)
StripWord() -- Removes first word in character string.
               Usage: StripWord(<cW>)
Plural()    -- Returns the "plural" of a noun. This will fit most cases, but not
               all, as English has too many exceptions. 
               Usage: Plural(<nItems>,"<cNoun>")
StrComp()   -- Compares the contents of two strings.
               Usage: StrComp(<cStr1>,<cStr2>)
StrOccur()  -- Calculates the number of occurences of a string in another,
               works for character memvar/field, and memo fields.
               Usage: StrOccur(<cInString>,<cFindString>)
NumOccur()  -- Calculates the number of occurences of a string in another.
               Usage: NumOccur(<cInString>,<cFindString>)
ReplMemo()  -- Globally searches and replaces a string with another string
               in a character field/memvar or memo field.
               Usage: ReplMemo(<cSource>,<cCurrStr>,<cNewStr>)
MemStuff()  -- Replaces a specific string in a character string, by another.
               Returns the resultant string.
               Usage: MemStuff(<cSource>,<cCurrStr>,<cNewStr>)
Stub()      -- Returns a specific number of characters from a given string, 
               adding characters in cIn to the end of it.
               Usage: Stub(<cString>,<nIn>,<cIn>)
FirstMem()  -- Capitalizes the first character of all the words in the string
               passed as a parameter, returns resultant string (unless a memo,
               in which case, returns a .T.)
               Usage: FirstMem(<cInStr>)
FirstCap()  -- Capitalizes the first character of a string.
               Usage: FirstCap(<cInString>)

--------------------------------------------------------------------------------
CONVERT.PRG -- Numeric Conversions/calculations
--------------------------------------------------------------------------------
Roman()     -- Function to return a Roman Numeral based on input of an Arabic.
               Usage: Roman(<nArabic>)
Arabic()    -- Opposite of Roman (takes Roman Numeral provided, returns
               Arabic).
               Usage: Arabic("<cRoman>")
Factorial() -- Does what it sounds like, it returns the factorial of a value.
               Usage: Factorial(<nNumber>)
IsPrime()   -- Determines if the argument passed is a prime positive integer.
               Usage: IsPrime(<nNumber>)
BankRound() -- Rounds numeric argument to given # of places using "Banker's 
               rule."
               Usage: BankRound(<nNumber>,<nPlaces>)
Num2Str()   -- Number to String, uses ASCII 1/2 and 1/4 instead of decimals
               where appropriate.
               Usage: Num2Str(<nNumber>)
Dec2Hex()   -- Decimal to Hexadecimal conversion.
               Usage: Dec2Hex(<nDecimal>)
Hex2Dec()   -- Hexadecimal to Decimal conversion.
               Usage: Hex2Dec(<cHex>)
Hex2Bin()   -- Hexadecimal to Binary conversion.
               Usage: Hex2Bin(<cHex>)
Bin2Hex()   -- Binary to Hexadecimal conversion.
               Usage: Bin2Hex(<cBin>)
Dec2Oct()   -- Decimal to Octal conversion.
               Usage: Dec2Oct(<nDec>)
Oct2Dec()   -- Octal to Decimal conversion.
               Usage: Oct2Dec(<xOct>)
Cash2Check()-- Converts a number of dollars and cents to a string of words.
               Usage: Cash2Check(<nCash>)
Num2Words() -- Converts an integer to a string of words.
               Usage: Num2Words(<nNum>)
Thou2Words()-- Converts a positive integer less than 1000 to a string of words.
               Usage: Thou2Words(<nNum>)
Ord()       -- Converts an integer to ordinal representation.
               Usage: Ord(<nNum>)
Num2Word()  -- Converts an integer to a string of words -- self-contained
               function, does not call other functions. 
               Usage: Num2Word(<nValue>)
Num2Real()  -- Converts a number to the ASCII representation of its storage in
               IEEE 8-byte real format.
               Usage: Num2Real(<nNum>,<nExp>)
Dec2Bin()   -- Decimal to Binary conversion.
               Usage: Dec2Bin(<nNum>,<nPlaces>)
Frac2Bin()  -- Converts the fractional part of a decimal number to a
               character string giving its ASCII binary representation.
               Usage: Frac2Bin(<nNum>,<nPlaces>)
Bin2Dec()   -- Converts a string containing a binary value to its numeric 
               (decimal) equivalent.
               Usage: Bin2Dec(<cStr>)
Dec2Mkd()   -- Decimal to echit chr() values in array. (Roughly equivalent to 
               MDK$() in BASIC)
               Usage: Dec2Mkd(<nVar>,<cName>)
Dec2Mki()   -- Converts an integer in range -32,768 to +32,767 to two chr() 
               values equivalent to the two bytes created by the BASIC MKI$().
               Usage: Dec2Mki(<nInt>,<cName>)
Dec2Mkl()   -- Converts integer to four chr() values in array. Equivalent to 
               MKL$() in BASIC.
               Usage: Dec2Mkl(<nInt>,<cName>)
Dec2Mks()   -- Converts numeric value to four chr() values in array. Equivalent 
               to MKS$() in BASIC.
               Usage: Dec2Mks(<nVar>,<cName>)
Dec2MSks()  -- Convert numeric to four CHR() values in array. Uses obsolete
               MicroSoft format. 
               Usage: Dec2MSks(<nVar>,<cName>)
Mkd2Dec()   -- Convert eight bytes storing an IEEE long real value (similar to
               CVD() function in BASIC)
               Usage: Mkd2Dec(<c1>,...,<c8>)
Mki2Dec()   -- Convert two bytes storing a signed short integer to decimal
               equivalent. Similar to CVI() in BASIC.
               Usage: Mki2Dec(<c1>,<c2>)
Mkl2Dec()   -- Convert four bytes storing a signed long integer. Similar to 
               CVL() in BASIC.
               Usage: Mkl2Dec(<c1>,<c2>,<c3>,<c4>)
Mks2Dec()   -- Converts four bytes storing an IEEE Short real value. Similar to
               CVS() in BASIC.
               Usage: Mks2Dec(<c1>,<c2>,<c3>,<c4>)
MSks2Dec()  -- Converts four bytes storing an old-style Microsoft short real
               value to decimal. Similar to CVS() in BASIC.
               Usage: MSks2Dec(<c1>,<c2>,<c3>,<c4>)
Ordinal()   -- Returns an ordinal string for a postiive integer < 100. For
               values greater than this, use Num2Words(), and use this for
               the values < 100.
               Usage: Ordinal(<nNum>)

--------------------------------------------------------------------------------
DATES.PRG -- Date Handling Routines
--------------------------------------------------------------------------------
DateText3() -- As DateText() and DateText2() in PROC.PRG, returns: Month, Year.
               Usage: DateText3(<dDate>)
Age2()      -- Returns age of someone on the date of a specific event.
               Usage: Age2(<dDate>,<dEvent>)
Annivrsry() -- Checks to see if a birthday or other specific "anniversary" is 
               within a range of dates.
               Usage: Annivrsry(<dTest>,<dBegin>,<dEnd>)
AddMonths() -- Returns the exact date 'N' months from give date.
               Usage: AddMonths(<dDate>,<nMonths>)
AddYears()  -- Returns the exact date 'N' Years from given date.
               Usage: AddYears(<dDate>,<nYears>)
IsLeap()    -- Returns .t./.f. if year is a leap year... (year in YY or YYYY
               formats)
               Usage: IsLeap(<nYear>)
DoY()       -- Day of Year -- returns "Julian" date (US Government version ...)
               -- this is the number of days a date is from January 1 of that
               year (i.e., 11/14/91 = 318).
               Usage: DoY(<dDate>)
WeekNo()    -- Returns the week number of the date (there are 52 weeks a year,
               right?). 
               Usage: WeekNo(<dDate>)
Holiday()   -- Returns the date of specific "floating" holidays for a given
               year, requires a one-letter code. See full doc in DATES.PRG.
               Usage: Holiday(<nYear>,<cCode>)
               Where cCode may be one of the following:
                     P = President's Day
                     D = Daylight Saving Time
                     M = Memorial Day
                     L = Labor Day
                     C = Columbus Day
                     S = Return to "Standard" Time
                     E = Election Day
                     T = Thanksgiving Day
                     A = Advent 1st Sunday
EasterDay() -- This returns the day of Easter. It doesn't work as easily as
               those dates given above, so has it's own function.
               Usage: EasterDay(<nYear>) && nYear = YYYY format
nDoW()      -- Numeric Day of Week -- used to return the numeric value of a 
               character day of the week, useful for some of the revised
               functions below.
               Usage: nDoW(<cDay>)
FWDoM()     -- First Working Day Of the Month -- this returns the first working
               day of the month passed to the function.
               Usage: FWDoM(<dDate>)
LWDoM()     -- Last Working Day Of the Month --  returns the last working day
               of the month passed to the function.
               Usage: LWDoM(<dDate>)
FDoD()      -- First Day of Date -- this returns the first occurrence of a given
               day of the week within a month. For example, you might need the
               first Monday of the month. 
               Usage: FDoD(<dDate>,"<cDay>")  (cDay = Monday, Tuesday, etc.)
LDoD()      -- Last Day of Date -- This returns the last occurrence of a given
               day of the week within a month. For example, you might need the 
               last Monday in a month.
               Usage: LDoD(<dDate>,"<cDay>")
LDoM()      -- Last Day of Month -- this returns the last day of the month
               as a date. It's used in LDoD and LWDoM above.
               Usage: LDoM(<dDate>)
NumDoD()    -- Number of Day of Date -- this returns a specific occurrence of a
               given day of the week within a month. For example, you might need
               the 3rd Tuesday of the month.
               Usage: NumDoD(<dDate>,<nDay>,"<cDay>")
WDIF()      -- Work Days In the Future -- this is used to return the date based
               on a number of work-days from another date. For example, you 
               could find the date of the 10th work date from today (date())
               by using date(),10 as the parameters in the format below. This
               function can use a HOLIDAYS database to be more accurate, but
               you must create it in a specific format (see complete function 
               documentation in the file DATES.PRG).
               Usage: WDiF(<dStart>,nWDays)
StoD()      -- String to Date -- this returns a "normal" dBASE date from a
               character string containing formats of YYYYMMDD or YYMMDD.
               Usage: StoD("<cString>")
Quarter()   -- This function returns the "Quarter" of the year that a specified
               date is in ...
               Usage: Quarter(<dDate>)
Dat2Jul()   -- Convert dBASE date to Julian date
               Usage: Dat2Jul(<dDate>)
Jul2Dat()   -- Convert Julian date to dBASE date
               Usage: Jul2Dat(<nJulian>)
FrstNxtMth()-- Returns the first day of next month, given a date in 'current'
               month.
               Usage: FrstNxtMth(<dDate>)

--------------------------------------------------------------------------------
TIME.PRG Time Processing Routines
--------------------------------------------------------------------------------
Delay()     -- Delay loop in seconds.
               Usage: Delay(<nSeconds>)
Time2Sec()  -- Convert time string to seconds.
               Usage: Time2Sec(<cTime>)
Sec2Time()  -- Convert seconds to time string.
               Usage: Sec2Time(<nSeconds>)
DiffTime()  -- Calculate difference btween two time strings.
               Usage: DiffTime(<cTime1>,<cTime2>)
Civ2Mil()   -- Convert civilian time string (i.e., "12:59 A.M.") to 24 hour
               (military) time.
               Usage: Civ2Mil(<cCivilTime>)
Mil2Civ()   -- Convert military (24 hour) time to Civilian time.
               Usage: Mil2Civ(<cMilTime>)
IsAmPm()    -- Checks to see if a time string is in "Civilian" time format 
               (i.e., AM/PM) -- returns a logical (.t./.f.)
               Usage: IsAmPm(<cTime>)
   
--------------------------------------------------------------------------------
FINANCE.PRG -- Finance Functions
--------------------------------------------------------------------------------
Discount()  -- Compute the present value of an amount received at the end of
               a number of periods given a periodic interest rate.
               Usage: Discount(<nFuturVal>,<nRate>,<nPeriods>)
FuturVal()  -- Compute the future value of an initial amount at compound
               interest received at a given periodic rate for a number of 
               periods.
               Usage: FuturVal(<nPresVal>,<nRate>,<nPeriods>)
Rate()      -- Compute rate of periodic interest needed to produce a future
               value from a present value in a given number of periods.
               Usage: Rate(<nFutVal>,<nPresVal>,<nPeriods>)
ContRate()  -- Compute rate if compounding is continuous.
               Usage: ContRate(<nFutVal>,<nPresVal>,<nYears>)
NPV()       -- Net Present Value of array aCashFlow[n].
               Usage: NPV(<nRate>,<nPeriods>)
IRR()       -- Internal Rate of Return, using ZeroIn().
               Usage: Irr(<fX1>,<fX2>,<n_Flag>)

--------------------------------------------------------------------------------
ARRAY.PRG -- Array Processing Routines
--------------------------------------------------------------------------------
AFill()     -- Fills an array with sequential elements. Useful for testing
               array processing routines.
               Usage: FillArray(<aArray>,<nArraySize>,<nFirstValue>,<nStep>)
AMask()     -- Returns a "mask" specifying the desired row or column of an
               array.
               Usage: AMask(<cArrayskel>,<cVar>)
AMean()     -- Mean of non-blank numeric or date values in specified row or
               column of an array.
               Usage: AMean(<cArrayskel>)
AMax()      -- Maximum non-blank numeric, date or character value in specified
               row or column of an array.
               Usage: AMax(<cArrayskel>)
AMin()      -- Minimum non-blank numeric, date or character value in specified
               row or column of an array.
               Usage: AMin(<cArrayskel>)
AVar()      -- Finds population variance of non-blank numeric or date values
               in specified row or column of a specified array.
               Usage: AVar(<cArrayskel>)
ASeek()     -- Performs a binary search in any specified ascending-sorted row
               or column of an array.
               Usage: aSeek(<cFindItem>,<aArray>,<nArraySize>)
AShuffle()  -- Performs a shuffle of elements of an array randomly ...
               Usage: aShuffle(<aArray>,<nLength>)
ABubble()--    Performs a bubble sort (slow) on an array. By telling the
               routine the number of passes, you can have it stop at a specific
               point, and obtain some of the highest or lowest values, without
               taking the time to perform a complete sort. To perform a
               complete sort, pass the same value for nPasses as for nLength 
               (number of elements in array) -- if you want a complete sort,
               however, you may want to take another look at ShellSort()
               below ... it's faster.
               Usage: aBubble(<aArray>,<nLength>,<nPasses>)
ArrayRows() -- Returns number of rows (elements) in an array.
               Usage: ArrayRows(<aArray>)
ArrayCols() -- Returns number of columns in an array.
               Usage: ArrayCols(<aArray>)
ShellSort() -- Performs a fast sort routine on an array. This array must be
               copied into an array called: aMyArray. 
               Usage: ShellSort(<nNumber>)
ARec2Arr()  -- Creates a public array, aRecord[n], initialized to the record
               format of the currently selected DBF, either blank or filled
               with the values of the current record.
               Usage: ARec2Arr(<lBlank>)
aPullSort() -- Performs a sort on an array. This array must be copied into an
               array called: aMyArray. This routine is theoretically faster than
               the ShellSort() routine above, and definitely faster than the
               aBubble() routine above.
               Usage: aPullSort(<nNumber>)

--------------------------------------------------------------------------------
MEASURE.PRG -- Conversion of Measurements
--------------------------------------------------------------------------------
Kg2Lb()     -- Used to convert Kilograms to Pounds.
               Usage: Kg2Lb(<nKg>)
Lb2Kg()     -- Used to convert Pounds to Kilograms.
               Usage: Lb2Kg(<nPounds>)
Inch2Cm()   -- Inches to Centimeters.
               Usage: Inch2Cm(<nInches>)
Cm2Inch()   -- Centimeters to Inches.
               Usage: Cm2Inch(<nCm>)
Km2Mile()   -- Kilometers to Miles.
               Usage: Km2Mile(<nKm>)
Mile2Km()   -- Miles to Kilometers.
               Usage: Mile2Km(<nMiles>)
Km2Naut()   -- Kilometers to Nautical miles.
               Usage: Km2Naut(<nKm>)
Naut2Km()   -- Nautical miles to Kilometers.
               Usage: Naut2Km(<nNautMiles>)
Naut2Stat() -- Nautical miles to Statute miles (approximate).
               Usage: Naut2Stat(<nNautMiles>)
Stat2Naut() -- Statute miles to Nautical miles (approximate).
               Usage: Stat2Naut(<nStatMiles>)
Fahr2Cel()  -- Fahrenheit to Celsius.
               Usage: Fahr2Cel(<nFahrTemp>)
Cel2Fahr()  -- Celsius to Fahrenheit.
               Usage: Cel2Fahr(<nCelTemp>)
Gal2Ltr()   -- US Gallons to Liters
               Usage: Gal2Ltr(<nGal>)
Ltr2Gal()   -- Liters to US Gallons
               Usage: Ltr2Gal(<nLiters>)
CuFt2Gal()  -- Cubic feet to US Gallons
               Usage: CuFt2Gal(<nCubicFeet>)
Gal2CuFt()  -- US Gallons to Cubic Feet
               Usage: Gal2CuFt(<nGallons>)

--------------------------------------------------------------------------------
TRIG.PRG -- Trigonometric Functions
--------------------------------------------------------------------------------
Note, all of these have the Usage:  FUNC(<nX>)

Secant()    -- Secant of an angle X in radians.
Cosecant()  -- CoSecant of an angle X in radians.
CoTan()     -- CoTangent of an angle X in radians.
ASec()      -- Inverse Secant - angle size in radians.
ACoSec()    -- Inverse Cosecant - angle size in radians.
ACoT()      -- Inverse CoTangent
SinH()      -- Hyperbolic Sine
CosH()      -- Hyperbolic CoSine
TanH()      -- Hyperbolic Tangent
SecH()      -- Hyperbolic Secant
CScH()      -- Hyperbolic CoSecant
CoTH()      -- Hyperbolic CoTangent
ASinH()     -- Inverse Hyperbolic Sine
ACosH()     -- Inverse Hyperbolic CoSine
ATanH()     -- Inverse Hyperbolic Tangent
ASecH()     -- Inverse Hyperbolic Secant
ACscH()     -- Inverse Hyperbolic CoSecant
ACotH()     -- Inverse Hyperbolic Cotangent
Hav()       -- Haversine 
AHav()      -- Inverse Haversine

--------------------------------------------------------------------------------
NAVIGATE.PRG -- Navigation Routines
--------------------------------------------------------------------------------
Correct()   -- Correction of direction - adjusts direction given, in degrees,
               by a second number of degrees.
               Usage: Correct(<nDirection>,<xCorrection>)
UnCorrect() -- Uncorrection of direction - adjusts direction given, as above.
               This is the inverse of Correct().
               Usage: UnCorrect(<nDirection>,<xUnCorr>)
XAngle()    -- Angle in degrees (<=90) at which two vectors in degrees
               intersect.
               Usage: XAngle(<nVector1>,<nVector2>)
LeftWind()  -- Effect of second vector on first.
               Usage: LeftWind(<nCourse>,<nWindFrom>)
TailWind()  -- Is the effect of second vector on first additive?
               Usage: TailWind(<nCourse>,<nWindFrom>)
Heading()   -- Heading required to make good a course.
               Usage: Heading(<nCourse>,<nAirspeed>,<nWindFrom>,<nForce>)
Course()    -- Course made good given heading, speed, wind dir, and force.
               Usage: Course(<nCourse>,<nAirspeed>,<nWindFrom>,<nForce>)
GndSpeed()  -- Speed over the ground given heading, etc.
               Usage: GndSpeed(<nCourse>,<nAirspeed>,<nWindFrom>,<nForce>)
Deg2Num()   -- Degrees to numbers ... converts character description of
               degrees (Degrees Minutes Seconds:  40d50'30.2 N) to numeric
               value.
               Usage: Deg2Num("<cDms>")
BearsDist() -- Distance to an object at the time of the second bearing.
               Usage: BearsDist(<nBear1>,<nBear2>,<nRun>)
BearsPass() -- Distance at which an object will be when abeam given 2 bearings.
               Usage: BearsPass(<nBear1>,<nBear2>,<nRun>)
BearsRun()  -- Distance to run until object will be abeam given two bearings.
               Usage: BearsRun(<nBear1>,<nBear2>,<nRun>)
GCDist()    -- Great Circle distance between 2 points given latitude and long.
               of each. 
               Usage: GcDist(<cLat1>,<cLon1>,<cLat2>,<cLon2>)
GcCourse()  -- Initial Great Circle course between two points given lat and 
               long of each. (Following a 'Great Circle' requires course 
               changes.
               Usage: GcCourse(<cLat1>,<cLon1>,<cLat2>,<cLon2>)

--------------------------------------------------------------------------------
STATS.PRG -- Statistical Routines
--------------------------------------------------------------------------------
Samplevar() -- Finds sample variance of specified field of the current database.
               Usage: SampleVar(<cField>[,<cClause>])
Stny()      -- Returns value of the standard normal distribution function given
               a number of standard deviations from the mean.
               Usage: Stny(<nDevs>)
StnArea()   -- Area of the standard normal distribution function between mean
               and given number of standard deviations from the mean.
               Usage: StnArea(<nDevs>)
Stnz()      -- Lookup table to find the values of 'z', standard deviations,
               corresponding to the most common areas inside a given number
               of tails of the normal distribution function.
              Usage: Stnz(<nProb>,<nTails>)
StnDiff()   -- Determines whether hypothesis that sample of a given mean is
               different from expected mean is justified.
               Usage: StnDiff(<nConf>,<nTails>,<nSample>,<nSampMean>,;
                               <nPopMean>,<nPopStd>)
StnDevs()   -- Calculates 'z', standard deviations, corresponding to any
               area of standard normal curve between mean and the desired
               z. Much slower than Stnz().
               Usage: StnDevs(<nArea>)
TstnArea()  -- Translation function to convert area to left of point under
               standard normal curve to 0 for ZeroIn().
               Usage: TstnArea(<nDevs>,<nArea>)
ZeroIn()    -- Finds a zero of a continuous function.
               Usage: ZeroIn(<cFunction>,<fX1>,fX2>,<fAbsError>,<nMaxiter>,;
                              <n_Flag>)

--------------------------------------------------------------------------------
FIELDS.PRG -- Field Processing Routines
--------------------------------------------------------------------------------
MemoPagr()  -- Used to display a memo in a window on screen, allows user to
               scroll up and down through memo.
               Usage: MemoPagr("<cMemo>",<nULRow>,<nULCol>,<nBRRow>,<nBRCol>)
ScanMemo    -- Used to remove hard returns in all memo fields in all records
               of a specified database.
               Usage: Do ScanMemo with "<cDbf>"
Cut         -- Used to cut to a global memvar CLIPBOARD the contents of a field
               or memvar on screen (during a read) -- can then be used with
               PASTE.
               Usage: do Cut with "<cFld>","<cScrType>"
Copy        -- Used to COPY to a global memvar CLIPBOARD the contents of a
               field or memvar on screen, so it can be used with PASTE.
               Usage: do Copy with "<cFld>"
Paste       -- Used to paste the contents of CLIPBOARD (global memvar) to
               the current field.
               Usage: do Paste with "<cFld>","<cScrType>"
Blanker()   -- Used to blank out a numeric field upon input of a valid numeric
               item. Useful with GETs ...
               Usage: Blanker()
GetRange()  -- Get a range for use with "SET KEY" or "SET FILTER" commands,
               works with character, numeric, float and date types.
               Usage: GetRange(<cTitle>,<xPara1>,<xPara2>,<cPicture>,;
                               <nStartRow>,<cColor>[,<cStyle>])

--------------------------------------------------------------------------------
FILES.PRG -- File Handling Routines
--------------------------------------------------------------------------------
AllTags     -- Used to bring up a popup/picklist of MDX tags ... can be
               assigned to a function key.
               Usage: do AllTags with <nULRow>,<nULCol>
RedoTags    -- Used to deal with "bloated" MDX files. This will delete old
               tags and recreate the MDX file, reducing the size of it, and
               making access faster. 
               Usage: do RedoTags with "<cDBF>" && note, do not include ext.
AutoRedo    -- Used to bring up a picklist of DBF files, so that you (or the
               user) can choose which to redo the tags for.
               Usage: do AutoRedo with <nXTL>,<nYTL>,<nXBR>,<nYBR>,<cColor>)
PrntTags    -- Used to print a list of tags/expressions to either the printer
               or a file for a specific database.
               Usage: do PrntTags with "<cDBF>"
ListDBFs    -- Used to create a simple database (DBFS.DBF) containing the names
               of all databases in the current directory.
               Usage: do ListDBFs
ReCompile() -- Recompiles all dBASE source-code files. 
               Usage: Recompile([<cDir>],[,<cSkel>[,"R"]])
MakeDbf     -- Makes an empty DBF.
               Usage: Do MakeDbf with <cFileName>,<aArray>
MakeDbf2    -- Makes an empty DBF, assumes array aMakeDBF[n,5].
               Usage: Do MakeDBF with <cDBFpath>,<cStruPath>
MakeStru()  -- Makes an empty dBASE Structure EXTENDED file and returns its
               root name.
               Usage: MakeStru()
MakeStru2() -- Makes an empty dBASE Structure EXTENDED file, using dBASE print
               redirection. User/programmer may specify to save database
               in directory specified by DBTMP (DOS Environment variable) or
               in the current directory.
               Usage: MakeStru2(<lDBTmp>)
TempName()  -- Returns a name that can be used for a file of given extension
               without conflicting with names of existing files. If extension
               is 'DBF', assures that no .DBT or .MDX of that name exists as 
               well.
               Usage: TempName(<cExtension>,<lDBTmp>)
FileMove    -- Used to handle data entry/editing, allowing the user to move
               through the database by pressing specific keys. See internal
               docs for more detail.
               Usage: do FileMove with <nKey>
Used()      -- Checks to see if a database is currently in use -- returns a
               logical.
               Usage: Used("<cFile>")
MDXByte()   -- Used to set the MDX Byte in a DBF header ON or OFF.
               Usage: MDXByte(<cDBFPath>,<cOnOff>)
aDir()      -- Creates a public array GADIR[n,4] containing directory 
               information. It is limited to 292 files or less, depending on
               the memory available. Requires SEARCH.BIN.
               Usage: aDir(<cFMask>,<cBINPath>,<cAttr>)
DBFDir()    -- Creates (or Overwrites) DBDDIR.DBF, and populates it with
               directory information. Uses the DOS 5.0 DIR command, and requires
               DOS 5.0. DO NOT ATTEMPT TO USE WITH PREVIOUS VERSIONS OF DOS.
               Usage: DBFDir(<cPathSkel>,<lHidSys>)
ParsPath()  -- Extracts and returns the path from a full path file 
               specification.
               Usage: ParsPath(<cFullPath>)
TagPop      -- Brings up a picklist of .MDX Tags for current database, so user
               can change sequence data is listed in. Lists key, whether or not
               tag has a 'for' clause or is unique, and gives most (if not all)
               of expression for the tag.
               Usage: do TagPop
AAppend()   -- Appends a text file into an array. This routine is limited to
               text files of 1,170 lines, and 254 characters per line. The
               text file must be an ASCII .TXT formatted file. Warning -- if
               array already exists, it will be overwritten.
               Usage: AAppend(<cFileName>,<aArrayName>)
FDel()      -- Deletes a given portion of a file (text or binary) from the
               beginning of the file, end of the file, or current pointer
               position. 
               Usage: FDel(<nHandle>,<nBytes>,<nStart>)
FGetLine()  -- Extracts a line of text from a text file.
               Usage: FGetLine(<cFileName>,<cLookup>[,<lCase>[,<lEntire>]])
FIns()      -- Inserts specified number of nulls into a low-level file. See
               comments on FDel().
               Usage: FIns(<nHandle>,<nBytes>,<nStart>)
GetInfo()   -- Retrieves information from STATUS that you cannot get with the
               dBASE IV function SET(). Keywords are:
                   WORK       Number of work area currently in
                   PRINT      Current printer destination (PRN, NUL, etc.)
                   ERROR      Error condition set by ON ERROR
                   ESCAPE     Escape condition set by ON ESCAPE
                   F2 to F10
                   Ctrl-F1 to Ctrl-F10
                   Shift-F1 to Shift-F10
                              Current setting of each key as set by SET FUNCTION
                   PAGE,LINE  Line number specified by ON PAGE AT LINE
                   HANDLE,<filename>
                              Handle number of low-level file <filename>
                   NAME,<filehandle>
                              Filename of low-level file specified by 
                                <filehandle>
                   MODE,<filehandle>
                              Privilege of low-level file spec. by <filehandle>
               Usage: GetInfo(<cKeyWord>[,<cKeyWord2>])
TextLine()  -- Returns the number of lines of text in an ASCII Text file.
               Usage: TextLine(<cTextFile>)
TLine()     -- Returns a specific line in an ASCII Text File.
               Usage: TLine(<cTextFile>,<nLine>)
TLineNo()   -- Returns the line number of the phrase you are searching for
               in an ASCII Text File.
               Usage: TLineNO(<cTextFile>,<cLookup>[,<lCase])
TempFile()  -- Returns a random filename in temporary directory.
               Usage: TempFile([cFileExt])
TempDir()   -- Returns path of temporary directory as set from DOS (i.e.,
               SET DBTMP=...).

--------------------------------------------------------------------------------
MISC.PRG -- Miscellaneous Routines
--------------------------------------------------------------------------------
PlayIt()    -- Plays a song based on parameter passed. 1 = Dirge, 
               2 = "touchdown", programmer may add more as needed ...
               Usage: PlayIt(<nSong>)
PageEst     -- Will estimate number of pages in a report, and then ask if you
               wish to generate said report ... requires three parameters:
               nCount = record count (may be 0, in which case procedure will
                        try to count the records)
               cReport = report name, with any FOR condition you wish -- if
                         you use a FOR condition, and give a '0' for the nCount
                         parameter, the procedure will count the records that
                         match the FOR (only a FOR is setup at the moment).
               nRecords = number of records that will print on a page. If you
                         send '0', the procedure will calculate based on 60 
                         records to the page.
               Usage: do PageEst with <nCount>,"<cReport>",<nRecords>
Permutes()  -- Permutations of a number of items taken x amount at a time.
               Usage: Permutes(<nNum>,<nHowMany>
Combos()    -- Combinations, similar to above -- slight difference. See docs.
               Usage: Combos(<nNum>,<nHowMany>)
BinLoad()   -- A function used to manage .BIN files.
               Usage: BinLoad(<cBinName>)
DialUp()    -- A simple dialer routine. (No longer requires LOWLEVEL.BIN)
               Usage: DialUp(<cPhoneNo>)
CurrPort()  -- Returns the current port being used by the SET PRINT command.
               Requires a database (CURRPORT.DBF, one field, 80 characters,
               called CURRPRT, indexed on said field ...)
               Usage: CurrPort()
FileLock()  -- Returns a logical if an attempt to lock a file on a LAN was
               successful, displays a message otherwise.
               Usage: FileLock("<cColor>")
RecLock()   -- Returns a logical if an attempt to lock a record on a LAN was
               successful, displays a message otherwise.
               Usage: RecLock("<cColor>")
UserID()    -- Returns the userid of the current user on a LAN. Returns a null
               string if not on a LAN.
               ** IF USING dBASE IV, 1.1 or less, requires USERID.BIN **
               Usage: UserID()
DosShell    -- Swaps out dBASE from memory, loads a DOS shell.
               Usage: do DosShell with <cAppName>
IsDisk()    -- Checks a disk in a disk drive to see if it's valid (door open,
               unformatted disk, etc.). ** Uses DISK.BIN **
               Usage: IsDisk("<cDrive>","<cColMess>","<cColErr>")
BlankIt     -- Used to act like a screen saver for dBASE. Displays a clock
               on the screen, waits for user to press <Esc> key.
               Usage: do BlankIt
               (suggest: ON KEY LABEL ALT-B DO BlankIt)
ClockIt     -- Used as part of BlankIt routine.
Clock       -- Same.
AuxMsg()    -- Will send output to a secondary monitor, if OX.SYS is loaded
               (via CONFIG.SYS).
               Usage: AuxMsg(<cMsg>,<lLF>)
GCD()       -- Greatest Common Divisor of two integers. Usually known as
               Euclid's Algorithm. 
               Usage: GCD(<n1>,<n2>)
RandSel()   -- Random Selection of Integers. Note that version 1.1 users
               will need to make some minor changes to this routine.
               Usage: RandSel(<nN>,<nT>[,<cArray>[,<lReSeed>]])

--------------------------------------------------------------------------------
PICKLIST.PRG -- "Generic" Picklist Routines
--------------------------------------------------------------------------------
Pick1()     -- Ken Holloway's generic picklist routine, allows user entering
               first letter of item, tab to another column, back tab, and so 
               on. Pretty spiffy.
               Usage: Pick1(<cTitle>,<cDisplay>,<cReturn>,<cKey>,<nFromRow>,;
                            <nFromCol>,<nToRow>,<nToCol>,<cColor1>,<cColor2>)
Pick2()     -- This picklist routine creates a picklist that determines it's
               own location on the screen by calling a couple of other functions
               (below) (uses BROWSE command -- Malcom C. Rubel).
               Usage: Pick2("<cLookFile>","<cTag>","<cSrchFld>","cRetFld>",;
                            <nScrRow>,<nScrCol>)
ScrRow()    -- Returns the row position of the current 'Get'. If the memvar
               nScrRow already exists, it returns the value in that memvar.
               Usage: ScrRow()
ScrCol()    -- Returns the column position of the current 'Get'. Works like 
               above, but for column.
               Usage: ScrCol()
Pick3       -- Martin Leon's DIYPOP routine. 
               Usage: do Pick2 with <cFields>,<nULRow>,<nULCol>,<nBRRow>,;
                                    <nBRCol>,<cNormCol>,<cFieldCol>,<cBorder>
Pick4()     -- Keith G. Chuvala's black-box picklist routine. This one's
               another rather spiffy routine. Includes selection of file,
               order and a "set key to" parameter, and ability to return
               value in the "normal" return manner, or to keyboard into
               a field.
               Usage: Pick4(<nRow>,<nCol>,<cTitle>,<cFileSpecs>,<cListWhat>,;
                            <nRetChar>,<nReturnType>,cColors)

--------------------------------------------------------------------------------
SCA.PRG -- SCA Date Handling Routines
--------------------------------------------------------------------------------
SCA_Real    -- Special purpose for SCA (Society for Creative Anachronism),
               brings up a window, enter date in SCA dates, converts to "real"
               dates (dBASE format).
               Usage: do SCA_Real
SCA2Real()  -- This function works like SCA_Real, without the user-input.
               Usage: SCA2Real(<cDay>,<cMonth>,<cYear>) && cyear=Roman Numeral
Real_SCA()  -- Used to convert 'real' (dBASE format) dates into SCA dates.
               (see SCA_Real Procedure above)
               Usage: Real_SCA(<dDate>)

--------------------------------------------------------------------------------
FRPG.PRG -- FRPG (Fantasy Role-Playing Games) ROUTINES
--------------------------------------------------------------------------------
SetRand     -- Procedure used to set a random # table, based on the time it
               is called, multiplied by the seconds at that moment. Useful
               for calling before using any of routines below. Used ONCE
               in a dBASE session, should be enough. The reason for this
               procedure is that I have found that using RAND(-1) often returns
               exactly the same values if the exact same function call (i.e.,
               Dice() below) is made several times. This doesn't, therefore,
               do what I want. By using the current TIME, I can get a different
               random number table each time. Use EITHER this function OR
               RAND(-1) during any one session of dBASE.
Dice()      -- Used to simulate the roll of a dice, will handle different types
               of dice (for FRPG type games, where you have 4,6,8,10,12,20,100
               sided dice ...)
               Usage: Dice(<nSides>)
MultDice()  -- As above but for multiple die (more than one).
               Usage: MultDice(<nNum>,<nSides>)
ValiDice()  -- Asks a gamer to enter a valid die roll, GM/Programmer specifies
               # of dice, number of sides ... (i.e., 3d6 is 3 six-sided dice,
               if GM says: 3,6 the program will ask for a value from 3 to 18,
               and not allow any other input).
               Usage: ValiDice(<nNum>,<nSides>,"<cMessage>","<cColor>")
DiceChoose()-- Presents three choices (in menu format) for gamer to use, die
               dice rolls ...
               Usage: DiceChoose(<nNum>,<nSides>,"<cMessage>","<cColor>")
ParseDice() -- Used to parse character field/memvar for xdy+z format of dice
               (a standard gaming format) and evaluate the value. I.e.,
               3d6+1 = 3 six-sided dice, +1 for each die rolled, giving a
               range from 6 to 21 -- function will return random number in 
               that range (actually "rolling" 3 six-sided dice, adding 1 in
               example). 
               Usage: ParseDice("<cDiceString>")
PopDice        Used to popup a place the user can enter a quick die roll, and
               have the computer do the actual dice rolling. Handy little
               routine ...
               Usage: do PopDice with <cColor>
               Example: ON KEY LABEL ALT-D DO POPDICE WITH "rg+/rg,w+/n,rg+/rg"

--------------------------------------------------------------------------------
WINDOWS.PRG -- People are beginning to want things that look like MicroSoft
Windows. Here are routines that do some of that. 
--------------------------------------------------------------------------------
Alert()      -- A popup with an "OK" pad, designed to force the user to
                acknowledge the message.
                Usage: Alert("<cTitle>","<cMessage>")
CheckBox()   -- One line message, with a check box to change the status of
                a logical memvar.
                Usage: CheckBox(<lVar>,"<cTitle>",<nRow>,<nCol>,<nAscii>)
CheckBx1()   -- Same as above, but is programmed a bit differently.
                Usage: CheckBx1(<lVar>,"<cTitle>",<nRow>,<nCol>)
DropDown()   -- Performs a picklist with an array, or a field in a database.
                Holds a choice in a holding area, allowing user to use that,
                or select something else.
                Usage: DropDown("<cType>","<cName>",[<nRow,[<nCol>,[<nSize>]]])
MSWind()     -- Creates a window that acts like a "MS Windows" window, in that
                you can move it, enlarge it to full screen, and bring it
                back to its original size.
                Usage: MSWind(<nTop>,<nLeft>,<nLower>,<nRight>)
Enlarge      -- Routine used with MSWIND() above to enlarge the window.
                Usage: do Enlarge
MoveWinU     -- Routine used to Move the window (MSWIND()) up on the screen.
                Usage: do MoveWinU
MoveWinD     -- Same as above to move window (MSWIND()) down.
                Usage: do MoveWinD
MSWinAct     -- Used to perform action(s) inside the window (MSWIND()).
                This routine should be modified for each specific system ...
                This one is just a sample ...
                Usage: do MSWinAct with <nTop>,<nLeft>
RadioBut()   -- Radio Button routine.
                Usage: RadioBut("<cArray>",<nRow>,<nCol>,<nDefPad>,<nAscii>)
TmpRadio     -- Used to set/reset temporary array aTmpRadio used with RadioBut()
                routine above.
                Usage: Do TmpRadio
ScrolBar()   -- Performs a horizontal scroll-bar to find a record in a database
                file.
                Usage: ScrolBar(<nAtLine>)
MSWind2()    -- Acts like above, but title (due to a ... feature ... of dBASE IV
                version 1.5) does not display if enlarged.
                Usage: MsWind2(<nTop>,<nLeft>,<nLower>,<nRight>,"<cColor>",;
                               "<cTitle>")
Enlarge2     -- Used with MSWind2() to enlarge to full-screen.
                Usage: do Enlarge2 with cTitle, cTitlCol
MoveWind     -- Used with MSWind2() to move the window.
                Usage: do MoveWin with <pPad>
MSWinAt2     -- Used to perform an action inside the window from MSWind2().
                Usage: do MSWinAt2
FieldNum()   -- Used to return the number of a given fieldname in the database
                structure. Works only on an open database.
                Usage: FieldNum("<cFldName>")

--------------------------------------------------------------------------------
ERRLOG.PRG -- A program to hold error-handling routines for dBASE IV.
--------------------------------------------------------------------------------
ErrorLog     -- This is used to generate an errorlog for the programmer,
                giving much vital information about the system at the time
                a program bombed. It can print the screen to disk as well
                as to paper, and can send a Novell Netware message to the
                programmer as well. (If you use print screen to paper or disk,
                you will require the use of PRINTSCR.BIN and/or SCREEN.BIN.)
                Usage: Do ErrorLog with error(),lineno(),program(),alias(),;
                          memory()[,<lPrntScrn>[,<lScrn2Disk>[,<cNetId>]]])

--------------------------------------------------------------------------------
OBSOLETE.PRG -- These are functions that, due to the advent of dBASE IV, 1.5,
(or other reasons) are no longer necessary. However, if you are a user of 1.1,
and/or wish to still use these functions, they are still available, but with
little support.
--------------------------------------------------------------------------------
Empty()     -- Returns a logical (.t. or .f.) if a field or memvar is empty. 
               In release 1.5 this is replaced with the internal function: 
               ISBLANK().
               Usage: Empty(<cField>)
               Recommendation: If creating a system that uses both dBASE IV
               versions 1.5 and earlier versions, rename this function to 
               ISBLANK(). If the system is an earlier version of dBASE, this
               function will be used, and if 1.5 or later, the internal function
               will be used.
NumFlds()   -- Counts the fields in a given database. This is replaced in 
               version 1.5 of dBASE IV with FLDCOUNT().
               Usage: NumFlds(<cDBF>)
DateSet()   -- Returns a string giving name of current DATE format.
               Usage: DateSet()
StampVal()  -- Evaluates a 16-character string in the form of the rightmost 
               16 characters returned by the DOS DIR command for a file.
               Usage: StampVal(<cTimeStamp>)
FullWin     -- Handy to overlay a screen with a full-screen window ...
               Usage: do FullWin with "<cColor>","<cWinName>","<cScreen>"
SetColor    -- used to set a memory file with colors, or load colors into
               memory variables from a memory file.
               Usage: do SetColor
SetColor2   -- used to set a mem file as above, but asks for a parameter to
               be sent, so that when designing a system, you can ask the
               user if their monitor is color or mono ... you pass "Y" or
               "N" ... i.e.,
               Usage: do SetColor2 with "<cYN>"
ExtrClr()   -- Used to extract the first parameter of a color memory variable.
               Usage: ExtrClr(<cColorVar>)
InvClr()    -- Can invert the colors of a color memory variable.
               Usage: InvClr(<cColorVar>)

--------------------------------------------------------------------------------
Enjoy. Happy computing. 

KJM
--------------------------------------------------------------------------------
-- EoF: README.TXT
--------------------------------------------------------------------------------
