[HandTools User's Guide]

Functional Overview of HandTools

The HandTools CDF library is shipped in eight separate .EXE files: HTCDF.EXE, CORECDF.EXE, BITSCDF.EXE, MACROCDF.EXE, DE45SYS.EXE, ARRAYCDF, PRINTCDF.EXE and DOSCDF.EXE.

HTCDF contains ALL of the functions included with HandTools in one CDF library. We recommend that you start out using only HTCDF. The other libraries included contain individual sub-sets of HTCDF that can be useful when you wish to use a particular set of features without incurring the overhead from the other functions that you don't use. If you find yourself only using a single particular set of features that are self-contained in one of the smaller libraries, then you may switch to using only that library and free up some memory for other things. See chapter 1 for more information on switching the location of a function library.

HandTools actually is comprised of seven 'families' of functions, with each family designed to address some need or deficiency in DataEase. Almost nobody will use all of the families in a given application, but almost everyone will come to depend on some of HandTools functions.

The Core family contains general-purpose functions that are likely to be of use to any serious developer. Its focus is broad and far-reaching. Core contains functions designed for utter convenience and efficiency.

The Presentations family contains the more sophisticated 'bells-and-whistles' of HandTools and is concerned with the presentation and appearance of information. Included are functions that allow you to create exploding windows, custom prompts, a fancy report browser, etc.

The Keyboard family contains functions for manipulating the keyboard and provides a facility for recording and playing back keyboard macros. You will find functions here that allow you to disable keys and force Ctrl-F10 lookup lists on the screen automatically.

The DataEase Internals family is perhaps the most useful family for the professional consultant, as it provides access and control over DataEase version 4.5x internal information. This family allows one to build automated system documentation reports, intelligent system maintenance procedures, and to complete previously impossible tasks such as specifying the source file for an import specification at run-time without asking the user anything. It also provides some powerful 'super' functions such as UndeleteAllRecords, GetTotalDBSize, and CreateImportFile.

The Array family provides a group of array functions that facilitate the construction of cross-tab reports.

The Programmer's family contains bit-wise logical functions for use by real digit-heads.

The Printer Redirection family provides the ability to specify a report's output at run-time without popping the confusing Print Style Specification form on the screen. HandTools provides a limited, but useful, LPT port redirector. By calling the redirection function from inside the DQL query, you can cause output intended for LPT1 in the Print Style Spec to go to a file, or to both LPT1 and the file, or the screen.

The library HTCDF.EXE contains all seven families. In addition, each family has been shipped in its own separate library for application in memory-constrained environments.

Functions that Return and Use 'Handles'

Many of the functions accept and return values called 'Handles'. Handles come into play when a CDF library provides the services of an 'object' to your DataEase application. Examples of objects that HandTools can provide to your application include display windows, arrays, or text files. A handle is a 'unique primary key', if you will, that identifies the object you are working with.

A handle is returned when an object managed by the CDF program is created, such as when you create an array with a call to InitArray(). When HandTools provides objects for your application to use, there will generally be one function provided that creates the object, one function that destroys the object and several that allow your application to interact with the object. The function that creates an object returns the new object's handle value. Those functions that interact with and destroy objects require that your application provide this handle value as an input parameter so that it knows which object you wish to work with. Therefore, handle values must be preserved in the calling DQL procedure or form until the object is properly disposed of.

It is important to remember to destroy objects after you are through using them. Otherwise, resources used by the object will not be relinquished until the CDF library program is unloaded.

Function Results and Input Parameters

All CDF functions return a result. In some cases this result is significant and your desire for this value may be the very reason you requested the function in the first place. In many other cases, however, the CDF function performs a service or a procedure and the function may not necessarily yield a single meaningful result upon whose specific value your application's successful execution ultimately depends.

A good example of such a function is CRTWrite, which simply writes text to the screen at a particular location. This function returns a numeric result code which can indicate success or failure, but, since there is virtually no way the function can fail, we aren't usually going to be interested in preserving or examining this function's result value. However, in procedures it is required that the result of a function be assigned to something, so, for this purpose, we usually define general purpose numeric (X) and text (S) variables so that the statement can appear as:

X := CRTWrite(2,1, "Now Processing Record ....",0,"") .

within a procedure.

It should be noted that most functions return a value that at least indicates whether or not the function actually executed or was prevented from executing due to some error in an input parameter. Normally you will not be concerned with these values unless you suspect there is a problem. Then, you will likely want to insert a Message statement in your procedure just after the function in question is executed so that you can examine the function's result to see if the CDF detected some error.

Trigger Parameters

In many of HandTools functions you will notice a reference to a text parameter called 'Trigger'. The Trigger parameter is never actually used by any function; it can be assigned any value you wish without consequence. So what good is it?

Consider a scenario where you want to program a virtual field's derivation formula to do these two things, in sequence, if a field called 'Test' contains any value other than 'S':

1) Beep.
2) Display a message that says: 'You may NOT do THAT!'

You could program two virtual fields to do this:

Field 1 Derivation:

If(Test not=S, Sound(2000, 100, 0, ""), blank)

Field 2 Derivation:

If(Test not=S, CRTWrite(2,1,"You may NOT do THAT!",1000,""), blank)

and it would work, though it would waste field space and be somewhat difficult to maintain, since there are two separate fields responding to the same condition.

Now, consider what the presence of the trigger parameter allows you to do. You can program one field derivation to perform the same function:

If(Test not=S, 
    CRTWrite(2,1,"You may NOT do THAT!",1000, Sound(2000, 100, 0, "")), 

By nesting the Sound function inside CRTWrite's trigger parameter, we can program the speaker to beep AND the message to be displayed using a single formula.

DataEase' parenthetical formula evaluation rules insure that the 'innermost' formula, parenthetically speaking, will be executed first, the next innermost, second, etc. By taking advantage of this rule and the presence of the nested trigger parameter, entire sequences, or procedures can be written in a single derivation formula! For example, we could modify the above example so that it:

1) Saves the current screen display
2) Clears the display screen
2) Beeps
3) Displays the message 'You may NOT do THAT!' for one second.
4) Restores the original screen appearance

by modifying the formula:

If(Test not=S, 
	CRTWrite(2,1,"You may NOT do THAT!",1000, 
	Sound(2000, 100, 0, 

As you can probably see, you can use the trigger parameter to great advantage.

HandTools' Functional Groups

HandTools is provided in seven CDF executable files: HTCDF, CORECDF.EXE, MACROCDF.EXE, DE45SYS.EXE, BITSCDF.EXE, PRINTCDF.EXE, and DOSCDF.EXE. HTCDF contains all of HandTool's functions in a single library, while each of the other libraries provide a subset of HTCDF's functions, grouped by logical operation.


HTCDF contains the entire HandTools suite of functions. It is recommended that you employ HTCDF for your applications unless you have a significant memory constraint or you are limiting your use of HandTools to those functions contained in one of the libraries described below, which are sub-sets of HTCDF.


CORECDF contains the core functions of HandTools. That is, the functions one is most likely to require while building a typical application. CORECDF.EXE provides a number of functional groups:

  • DOS system functions
  • Basic screen output
  • Basic keyboard input
  • Basic file input/output
  • Text manipulation
  • Numeric formatting representation
  • Unique Key Generator
  • Hayes-Compatible Modem Dialing
  • Class 1, Class 2, and CAS fax modem facsimile transmission


MACROCDF provides functions for the recording and playback of keyboard macros as well as for simulating keyboard input.


BITSCDF contains functions for bitwise manipulation and interpretation of data.


ARRAYCDF provides the ability to easily create arrays for cross-tab reports.


DE45SYS contains functions that allow your applications to query and manipulate DataEase internal system information directly from a procedure or formula. This can be useful for documenting applications, writing automatic system maintenance procedures, and modifying import specifications at run-time when the source file name is unknown until run-time.


DOSCDF provides the most sophisticated functions in the library. DOSCDF primarily concerns itself informat presentation using window 'objects'. All of the CDFs produced by LANimation employed Object-Oriented Programming (OOP) methods. DOSCDF provides a number of functions for creating, manipulating, and destroying screen-window objects thatcan greatly enhance the appearance of an application. The window functions allow you to explode windows onto the screen, employ sound effects, do window-relative screen I/O, display the contents of a text file within a window, prompt for edited user input, and launch a complete file browsing utility from with a form or procedure.

Many will likely employ only two functions from DOSCDF: PromptUser and Browsefile. PromptUser provides an elegant method for retrieving edited, ad-hoc user input on demand. BrowseFile provides a full-blown file browsing utility that supports title row and column freezing (like a spreadsheet's title rows), custom titling, text searching, printing, and mouse devices. BrowseFile can be used to implement a report previewer (its original purpose) or a custom help system. DOSCDF is large, but is invaluable when your looking for that extra sizzle factor in your application.


PRINTCDF provides the run-time redirection of output from any LPTx port to the screen or a disk file. Previously, the only way to allow a user to choose a report's destination was to display the confusing Print Style specification screen. Using the functions in PRINTCDF, you can now control, with some caveats, where output is going to be printed from within a DQL procedure. Moreover, you can switch destinations in mid-procedure, and you may allow the output to print on its original destination as well as echoing the output to a different destination.


This web site best viewed with Microsoft Internet Explorer version 5.0 or higher