21.2. Terminal interaction

21.2.1. Command line editing with GNU readline
21.2.2. Macro EXT:WITH-KEYBOARD

List of Examples

21.1. Dialog with user using completion

See also Section 32.1, “Random Screen Access”.

21.2.1. Command line editing with GNU readline

Platform Dependent: Only in CLISP linked against the GNU readline library.

List of Examples

21.1. Dialog with user using completion

Input through *TERMINAL-IO* uses the GNU readline library. Arrow keys can be used to move within the input history. The TAB key completes the SYMBOL name or PATHNAME that is being typed. See readline user manual for general details and TAB key for CLISP-specific extensions.

Warning

The GNU readline library is not used (even when CLISP is linked against it) if the stdin and stdout do not both refer to the same terminal. This is determined by the function stdio_same_tty_p in file src/stream.d. In some exotic cases, e.g., when running under gdb in an rxvt window under Cygwin, this may be determined incorrectly.

See also Section 33.5, “Advanced Readline and History Functionality”.

Extending completion

Variable CUSTOM:*COMPLETION*The value should be a FUNCTION of 3 arguments: string, start and end, which bound the text to be completed. The return value should be the list, whose FIRST is the immediate replacement for the already typed text and REST is all the possible completions. If no completions are available, return NIL.

Function EXT:MAKE-COMPLETIONGiven a LIST of all valid inputs, return a valid value for CUSTOM:*COMPLETION*.

Function EXT:LONGEST-COMMON-PREFIXGiven a LIST of VECTORs, return the VECTOR which is their longest common prefix. VECTOR elements are compared using the :TEST argument. Useful when writing your own CUSTOM:*COMPLETION* functions.

Example 21.1. Dialog with user using completion

(defun read-user-line (prompt completions)
  (princ prompt *query-io*)
  (force-output *query-io*)
  (let ((custom:*completion* (ext:make-completion completions)))
    (read-line *query-io*)))
(read-user-line "??? " '("a" "z123" "z135" "b" "abcd"))
⇒ ??? ab TAB
⇒ ??? abcd
(read-user-line "??? " '("a" "z123" "z135" "b" "abcd"))
⇒ ??? TAB TAB
⇒ a abcd b z123 z135
⇒ ??? z TAB
⇒ ??? z1TAB TAB
⇒ z123 z135

To force the user to select one of the pre-specified inputs you need to do something like this:

(defun read-user-line (prompt)
  (princ prompt *query-io*)
  (force-output *query-io*)
  (read-line *query-io*))
(defun read-user-option (prompt options)
  (loop
    :with custom:*completion* = (ext:make-completion options)
    :for option = (read-user-line prompt)
    :when (find option options :text #'string=)
    :return options
    :do (format *query-io* "Invalid option ~S, please try again~%" option)))

Linking against GNU readline

For CLISP to use GNU readline it has to be detected by the configure process.

  • If you run it as

    $ ./configure --with-readline

    it will fail if it cannot find a valid modern GNU readline installation.

  • If you use the option --without-readline, it will not even try to find GNU readline.
  • The default behavior (--with-readline=default) is to use GNU readline if it is found and link CLISP without it otherwise.

You can find out whether GNU readline has been detected by running

$ grep HAVE_READLINE config.h

in your build directory.

21.2.2. Macro EXT:WITH-KEYBOARD

Platform Dependent: UNIX, Win32 platforms only.

*TERMINAL-IO* is not the only stream that communicates directly with the user: During execution of the body of a (EXT:WITH-KEYBOARD . body) form, EXT:*KEYBOARD-INPUT* is the STREAM that reads the keystrokes from the keyboard. It returns every keystroke in detail as an SYS::INPUT-CHARACTER with the following slots (see Section 13.4.1, “Input Characters” for accessing them):

char

the CHARACTER for standard keys (accessed with CHARACTER)

Note

For non-standard keys CHARACTER SIGNALs an ERROR, use EXT:CHAR-KEY:

(EXT:WITH-KEYBOARD
 (LOOP :for char = (READ-CHAR EXT:*KEYBOARD-INPUT*)
   :for key = (OR (EXT:CHAR-KEY char) (CHARACTER char))
   :do (PRINT (LIST char key))
   :when (EQL key #\Space) :return (LIST char key)))
key

the key name, for non-standard keys (accessed with EXT:CHAR-KEY):

Platform Dependent: UNIX, Win32 platforms only.
keyvalue
F1..F12:F1..:F12
Insert:INSERT
Delete:DELETE
Home:HOME
End:END
Center:CENTER
PgUp:PGUP
PgDn:PGDN
Arrow keys:LEFT :RIGHT :UP :DOWN
bits
:HYPER
(Platform Dependent: Win32 platform only.) if a non-standard key. These keys are: [Win32]: Function keys, cursor keypads, numeric keypad.
:SUPER
(Platform Dependent: Win32 platform only.) if pressed together with Shift key(s) and if the keystroke would have been different without Shift.
:CONTROL
if pressed together with the Control key.
:META
(Platform Dependent: Win32 platform only.) if pressed together with the Alternate key.
font
Always 0.

This keyboard input is not echoed on the screen. During execution of a (EXT:WITH-KEYBOARD . body) form, no input from *TERMINAL-IO* or any synonymous stream should be requested.

Warning

Since SYS::INPUT-CHARACTER is not a subtype of CHARACTER, READ-LINE on EXT:*KEYBOARD-INPUT* is illegal.


These notes document CLISP version 2.49.93+Last modified: 2018-02-19