\section{Line edit protocol}
\label{sec-edit-protocol}

\subsection{Protocol classes}

\Defclass {line}

This class is the base class for all lines.  It should not itself be
instantiated.  Instead, \sysname{} contains two different modules
each supplying a different subclass of \texttt{line} that can be
instantiated.

\Defclass {cursor}

This is the base class for all cursors.

\Definitarg {:line}

The class \texttt{cursor} accepts this initarg which is the line to
which the new cursor is to be attached.

\subsection{Operations on lines and cursors}

\Defgeneric {cursor-position} {cursor}

Return the position of \textit{cursor} in the line to which it is
attached.

\ifdetached{}

\Defgeneric {(setf cursor-position)} {new-position cursor}

Set the position of \textit{cursor} to \textit{new-position} in the line
to which \textit{cursor} is attached.

\ifdetached{}

If \textit{new-position} is negative, then a condition of type
\texttt{beginning-of-line} is signaled.  If \textit{new-position} is
strictly greater than the number of items in the line to which
\texttt{cursor} is attached (See the generic function
\texttt{item-count}), then a condition of type \texttt{end-of-line} is
signaled.

\Defgeneric {beginning-of-line-p} {cursor}

Return \textit{true} if and only if \textit{cursor} is located at the
beginning of the line to which \textit{cursor} is attached.

\ifdetached{}

Calling this function is equivalent to calling the function
\texttt{cursor-position} with \textit{cursor} as argument and
comparing the return value to $0$.  \howeverperformance{}

\Defgeneric {end-of-line-p} {cursor}

Return \textit{true} if and only if \textit{cursor} is located at the
end of the line to which \textit{cursor} is attached.

\ifdetached{}

Calling this function is equivalent to calling the function
\texttt{cursor-position} with \textit{cursor} as argument and
comparing the return value to the number of items in the line to which
\textit{cursor} is attached (See the generic function
\texttt{item-count}).  \howeverperformance{}

\Defgeneric {beginning-of-line} {cursor}

Position \textit{cursor} at the very beginning of the line to which it
is attached.

\ifdetached{}

Calling this function is equivalent to calling the function
\texttt{(setf cursor-position)} with $0$ and \textit{cursor} as
arguments.  \howeverperformance{}

\Defgeneric {end-of-line} {cursor}

Position \textit{cursor} at the very end of the line to which it
is attached.

\ifdetached{}

Calling this function is equivalent to calling the function
\texttt{(setf cursor-position)} with the number of items in the line
to which \textit{cursor} is attached (See generic function
\texttt{item-count}) and \textit{cursor} as arguments.
\howeverperformance{}

\Defgeneric {forward-item} {cursor}

Move \textit{cursor} forward one position.

\ifdetached{}

Calling this function is equivalent to incrementing the
\texttt{cursor-position} of \textit{cursor}.  \howeverperformance{}

\Defgeneric {backward-item} {cursor}

Move \textit{cursor} backward one position.

\ifdetached{}

Calling this function is equivalent to decrementing the
\texttt{cursor-position} of \textit{cursor}.  \howeverperformance{}

\Defgeneric {item-at-position} {line position}

Return the item located at \textit{position} in \textit{line}.

If \textit{position} is less than zero, a condition of type
\texttt{beginning-of-line} is signaled.  If \textit{position} is
greater than or equal to the number of items in \textit{line} (See the
definition of the generic function \texttt{item-count}.), a condition
of type \texttt{end-of-line} is signaled.

\Defgeneric {item-after-cursor} {cursor}

Return the item located immediately after \textit{cursor}.

\ifdetached{}

Calling this function is equivalent to calling
\texttt{item-at-position} with the line to which the cursor is
attached (see generic function \texttt{line}) and the position of
\textit{cursor} (see generic function \texttt{cursor-position}).
\howeverperformance{}

\Defgeneric {item-before-cursor} {cursor}

Return the item located immediately before \textit{cursor}.

\ifdetached{}

Calling this function is equivalent to calling
\texttt{item-at-position} with the line to which the cursor is
attached (see generic function \texttt{line}) and the position of
\textit{cursor} (see generic function \texttt{cursor-position}) minus
one.  \howeverperformance{}

\Defgeneric {insert-item-at-position} {line item position}

Insert \textit{item} into \textit{line} at \textit{position}.

If \textit{position} is less than zero, a condition of type
\texttt{beginning-of-line} is signaled.  If \textit{position} is
greater than the number of items in \textit{line} (See the definition
of the generic function \texttt{item-count}.), a condition of type
\texttt{end-of-line} is signaled.

After this operation completes, what happens to cursors located at
\textit{position} before the operation depends on the class of the
cursor and of \textit{line}.  The \texttt{standard-line}
implementation provides two kinds of cursors, namely
\emph{left-sticky} cursors and \emph{right-sticky} cursors.  For such
an implementation, after this operation completes, any left-sticky
cursor located at \textit{position} will be located before
\textit{item}, and any right-sticky cursor located \textit{position}
will be located after \textit{item}.

\Defgeneric {delete-item-at-position} {line position}

Delete the item at \textit{position} in \textit{line}.

If \textit{position} is less than zero, a condition of type
\texttt{beginning-of-line} is signaled.  If \textit{position} is
greater than or equal to the number of items in \textit{line} (See the
definition of the generic function \texttt{item-count}.), a condition
of type \texttt{end-of-line} is signaled.

\Defgeneric {insert-item} {cursor item}

Calling this function is equivalent to calling
\texttt{insert-item-at-position} with the line to which
\textit{cursor} is attached, \textit{item}, and the position of
\textit{cursor}.  \howeverperformance{}

\ifdetached{}

\Defgeneric {delete-item} {cursor}

Delete the item immediately after \emph{cursor}.

Calling this function is equivalent to calling
\texttt{delete-item-at-position} with the line to which
\textit{cursor} is attached and the position of \textit{cursor}.
\howeverperformance{}

\ifdetached{}

\Defgeneric {erase-item} {cursor}

Delete the item immediately before \emph{cursor}.

Calling this function is equivalent to calling
\texttt{delete-item-at-position} with the line to which
\textit{cursor} is attached and the position of \textit{cursor} minus
one.  \howeverperformance{}

\ifdetached{}

\Defgeneric {cursor-attached-p} {cursor}

Return \emph{true} if and only if \textit{cursor} is currently
attached to some line.

\Defgeneric {detach-cursor} {cursor}

Detach \textit{cursor} from the line to which it is attached.

If \textit{cursor} is already detached, a condition of type
\texttt{cursor-detached} is signaled.

\Defgeneric {attach-cursor} {cursor line \optional (position 0)}

Attach \textit{cursor} to \textit{line} at \textit{position}.  If
\textit{position} is supplied and it is greater than the number of
items in \textit{line}, the error condition \texttt{end-of-line} is
signaled.  If \textit{cursor} is already attached to a line, the error
condition \texttt{cursor-attached} is signaled.

\Defgeneric {item-count} {entity}

If \textit{entity} is a line, then return the number of items in that
line.  If \textit{entity} is a cursor, return the number of items in
the line in which \textit{cursor} is located.

If \textit{entity} is a cursor that is not currently attached to a
line, a condition of type \texttt{cursor-detached} is signaled.

Note: the argument \textit{entity} can also be a buffer, in which case
the total number of items is returned.
\seesec{sec-buffer-edit-protocol}

\Defgeneric {line} {cursor}

Return the line in which \textit{cursor} is located. 

\ifdetached{}

\Defgeneric {buffer} {entity}

Return the buffer of \textit{entity}.  If \textit{entity} is a line,
then return the buffer to which the line is attached.  If
\textit{entity} is a cursor, then return the buffer of the line to
which the cursor is attached.

If \textit{entity} is a cursor that is not currently attached to a
line, a condition of type \texttt{cursor-detached} is signaled.

If \textit{entity} is a line that is not currently attached to a
buffer, a condition of type \texttt{line-detached} is signaled.
