Previous Page TOC Next Page

Character User Interface (FMLI and ETI)

ETI Program Examples

Program Examples


The following programs demonstrate uses of low-level ETI (curses) functions. See the demonstration programs delivered on the ETI product diskettes for programs that use the high-level ETI functions.

The editor Program


This program illustrates how to use curses routines to write a screen editor. For simplicity, editor keeps the buffer in stdscr; obviously, a real screen editor would have a separate data structure for the buffer. This program has many other simplifications: no provision is made for files of any length other than the size of the screen, for lines longer than the width of the screen, or for control characters in the file.

Several points about this program are worth making. First, it uses the move(), mvaddstr(), flash(), wnoutrefresh() and clrtoeol() routines that are all discussed in this document.

Second, it also uses some curses routines that are not discussed in this document. For example, the function to write out a file uses the mvinch() routine, which returns a character in a window at a given position. The data structure used to write out a file does not keep track of the number of characters in a line or the number of lines in the file. so trailing blanks are eliminated when the file is written. The program also uses the insch(), delch(), insertln(), and deleteln() routines. These functions insert and delete a character or line. See curses(3X) for more information about these routines.

Third, the editor command interpreter accepts special keys, as well as ASCII characters. On one hand, new users find an editor that handles special keys easier to learn about. For example, it's easier for new users to use the arrow keys to move a cursor than it is to memorize that the letter h means left, j means down, k means up, and l means right. On the other hand, experienced users usually like having the ASCII characters to avoid moving their hands from the home row position to use special keys.

NOTE: Because not all terminals have arrow keys, your curses programs will work on more terminals if there is an ASCII character associated with each special key.

Fourth, the CTRL-L command illustrates a feature most programs using curses routines should have. Often some program beyond the control of the routines writes something to the screen (for instance, a broadcast message) or some line noise affects the screen so much that the routines cannot keep track of it. A user invoking editor can type CTRL-L, causing the screen to be cleared and redrawn with a call to wrefresh (curscr).

Finally, another important point is that the input command is terminated by CTRL-D, not the escape key. It is very tempting to use escape as a command, since escape is one of the few special keys available on every keyboard. (Return and break are the only others.) However, using escape as a separate key introduces an ambiguity. Most terminals use sequences of characters beginning with escape (i.e., escape sequences) to control the terminal and have special keys that send escape sequences to the computer. If a computer receives and escape from a terminal, it cannot tell whether the user depressed the escape key or whether a special key was pressed.

editor and other curses programs handle the ambiguity by setting a time. If another character is received during this time, and if that character might be the beginning of a special key, the program reads more input until either a full special key is read, the time out is reached, or a character is received that could not have been generated by a special key. While this strategy works most of the time, it is not foolproof. It is possible for the user to press escape, then to type another key quickly, which causes the curses program to think a special key has been pressed. Also, a pause occurs until the escape can be passed to the user program, resulting in a slower response to the escape key.

Many existing programs use escape as a fundamental command, which cannot be changed without infuriating a large class of users. These programs cannot make use of special keys without dealing with this ambiguity, and at best must resort to a time-out solution. The moral is clear: when designing your curses programs, avoid the escape key.

The highlight Program


This program illustrates a use of the routine attrset(). highlight reads a text file and uses embedded escape sequences to control attributes. \U turns on underlining, \B turns on bold, and \N restores the default output attributes.

Note the first call to scrollok(), a routine that we have not previously discussed (see curses(3X)). This routine allows the terminal to scroll if the file is longer than one screen. When an attempt is made to draw past the bottom of the screen, scrollok() automatically scrolls the terminal up a line and calls refresh().

The scatter Program


This program takes the first LINES - 1 lines of characters from the standard input and displays the characters on a terminal screen in a random order. For this program to work properly, the input file should not contain tabs or non-printing characters.

The show Program


This program pages through a file, showing one screen of its contents each time you depress the space bar. The program call cbreak() so that you can depress the space bar without having to hit return; it calls noecho() to prevent the space from echoing on the screen. The nonl() routine, which we have not previously discussed, is called to enable more cursor optimization. The idlok() routine, which we also have not discussed, is called to allow insert and delete line. (See curses(3X) for more information about these routines). Also notice that clrtoeol() and clrtobot() are called.

By creating an input file for show made up of screen-sized (about 24 lines) pages, each varying slightly from the previous page, nearly any exercise for a curses() program can be created. This type of input file is called a show script.

The two Program


This program pages through a file, writing one page to the terminal from which the program is invoked and the next page to the terminal name on the command line. it then waits for a space to by typed on either terminal and writes the next page to the terminal at which the space is typed.

The two program is just a simple example of a two-terminal curses program. It does not handle notification; instead, it requires the name and type of the second terminal on the command line. As written, the command "sleep 100000"must be typed at the second terminal to put it to sleep while the program runs, and the user of the first terminal must have both read and write permission on the second terminal.

The window Program


This example program demonstrated the use of multiple windows. The main display is kept in stdscr. When you start to put something other than what is in stdscr on the physical terminal screen temporarily, a new window is created covering part of the screen. A call to wrefresh() for that window causes it to be written over the stdscr image on the terminal screen. Calling refresh() on stdscr results in the original window being redrawn on the screen. Note the calls to the touchwin() routine (which we have not discussed -see curses(3X)) that occur before writing out a window over an existing window on the terminal screen. This routine prevents screen optimization in a curses program. If you have trouble refreshing a new window that overlaps an old window, it may be necessary to call touchwin() for the new window to get it completely written out.

The colors Program


This program creates two windows. All characters displayed in the first window will be in read, on a blue background. All characters displayed in the second window will be in yellow, on a magenta background.