Elisp: Interactive Form
A common way of getting user input is by the “interactive” form.
(interactive code_letter_and_promp_string)
The interactive
expression must come right after the doc string.
Example:
(defun ask-name (x) "Ask name." (interactive "sEnter your name: ") (message "Name: %s" x))
Purpose of Interactive Form
The interactive
has 2 purposes.
- Make elisp function callable as interactive command.
- A mechanism for passing arguments to function when called interactively.
A function with the interactive
clause is called a command, and can be called by execute-extended-command
【Alt+x】
Get String as Argument
(interactive "sprompt_string")
- Prompt user, pass as first argument of function as string.
(defun ask-name (x) "Ask name." (interactive "sEnter your name: ") (message "Name: %s" x))
Get Number as Argument
(interactive "nprompt_string")
- Prompt user, pass answer as first argument of function as string.
(defun ask-age (x) "Ask age." (interactive "nEnter your age: ") (message "Name: %d" x))
Get Region Begin End Positions as Argument
(interactive "r")
- Pass region begin and end as arguments to function.
(defun print-region-boundary (x y) "Prints region start and end positions" (interactive "r") (message "Region begin at: %d, end at: %d" x y))
Passing Interactive a List
(interactive list_expression)
-
Pass the list that's the value of list_expression to function as arguments.
This is the most general way of usinginteractive
. The list_expression can be any lisp code, it just need to return a list. The lisp code can contain prompts, such asread-string
,read-file-name
, etc. [see Elisp: Get User Input]
(defun do-something (x y) "Ask name and age" (interactive ;; complex code here that returns a list (list "Mary" 22)) (message "Name is: %s, Age is: %d" x y))
Ways to Call Interactive
There are 3 forms of interactive
:
(interactive)
- No argument. This simply makes the function as command, and does not pass any argument to the function.
(interactive string)
- The first character (or first few character in same cases) in string tells emacs how to interpret the user input (such as string, number, file name, directory name, regex, lisp expression, key stroke, etc) and what datatype (string, number, etc) it should be converted to as your function's argument. The rest of string are use as prompt. However, if string contains multiple lines, each line's beginning are taken as what-to-do code.
(interactive list)
-
This is the most general way to fill function arguments from user input. This list elements will be passed as arguments to your function. Usually, it's like this
(interactive some_lisp_code)
where some_lisp_code evaluates to a list.
There are about 30 string codes for interactive string
, the most useful are shown on this page.
For complete list of interactive code, see (info "(elisp) Defining Commands")
If your function takes multiple inputs, you can promp user multiple times, using a single interactive
call, with mulitple lines, each line begin with a prompt code.
(defun ask-name-and-age (x y) "Ask name and age" (interactive "sEnter you name: nEnter your age: ") (message "Name is: %s, Age is: %d" x y))