1
0
Fork 0
mirror of git://git.code.sf.net/p/zsh/code synced 2025-09-03 10:21:46 +02:00

17414: narrow-to-region save and restore.

This commit is contained in:
Peter Stephenson 2002-07-05 10:49:46 +00:00
parent 135db923be
commit 363079af76
3 changed files with 122 additions and 50 deletions

View file

@ -1,3 +1,9 @@
2002-07-05 Peter Stephenson <pws@csr.com>
* 17414: Doc/Zsh/contrib.yo, Functions/Zle/narrow-to-region:
allow narrow-to-region to save and restore state, a bit
like save-restriction in emacs only completely different.
2002-07-05 Sven Wischnowsky <wischnow@zsh.org>
* 17429: Src/Zle/complist.c: improve interactive mode when

View file

@ -477,15 +477,17 @@ example(bindkey '^Xf' insert-files)
)
tindex(narrow-to-region)
tindex(narrow-to-region-invisible)
xitem(tt(narrow-to-region [ -p) var(pre) tt(] [ -P) var(post) tt(] [ -n ] [) var(start) var(end) tt(]))
xitem(tt(narrow-to-region [ -p) var(pre) tt(] [ -P) var(post) tt(]))
xitem( tt([ -S) var(statepm) tt(| -R) var(statepm) tt(] [ -n ] [) var(start) var(end) tt(])))
item(tt(narrow-to-region-invisible))(
Narrow the editable portion of the buffer to the region between the cursor
and the mark, which may be in either order. The region may not be empty.
tt(narrow-to-region) may be used as a widget or called as a function from a
user-defined widget; by default, the text outside the editable area remains
visible. Various options and arguments are available when it is called as
a function.
visible. A tt(recursive-edit) is performed and the original widening
status is then restored. Various options and arguments are available when
it is called as a function.
The options tt(-p) var(pretext) and tt(-P) var(posttext) may be
used to replace the text before and after the display for the duration of
@ -498,16 +500,37 @@ will be made invisible.
Two numeric arguments may be given which will be used instead of the cursor
and mark positions.
The option tt(-S) var(statepm) is used to narrow according to the other
options while saving the original state in the parameter with name
var(statepm), while the option tt(-R) var(statepm) is used to restore the
state from the parameter; note in both cases the em(name) of the parameter
is required. In the second case, other options and arguments are
irrelevant. When this method is used, no tt(recursive-edit) is performed;
the calling widget should call this function with the option tt(-S),
perform its own editing on the command line or pass control to the user
via `tt(zle recursive-edit)', then call this function with the option
tt(-R). The argument var(statepm) must be a suitable name for an ordinary
parameter, except that parameters beginning with the prefix tt(_ntr_) are
reserved for use within tt(narrow-to-region). Typically the parameter will
be local to the calling function.
tt(narrow-to-region-invisible) is a simple widget which calls
tt(narrow-to-region) with arguments which replace any text outside the
region with `tt(...)'.
On return from both widgets, the display is restored by any zle command
The display is restored (and the widget returns) upon any zle command
which would usually cause the line to be accepted or aborted. Hence an
additional such command is required to accept or abort the current line.
The return status of both widgets is zero if the line was accepted, else
non-zero.
Here is a trivial example of a widget using this feature.
example(local state
narrow-to-region -p $'Editing restricted region\n' \
-P '' -S state
zle recursive-edit
narrow-to-region -R state)
)
tindex(predict-on)
tindex(predict-off)

View file

@ -8,75 +8,118 @@
# Other options:
# -p pretext show `pretext' instead of the buffer text before the region.
# -P posttext show `posttext' instead of the buffer text after the region.
# Either or both may be empty.
# -n Only replace the text before or after the region with
# the -p or -P options if the text was not empty.
# Either or both may be empty.
# -S statevar
# -R statevar
# Save or restore the state in/from the parameter named statevar. In
# either case no recursive editing takes place; this will typically be
# done within the calling function between calls with -S and -R. The
# statevar may not begin with the prefix _ntr_ which is reserved for
# parameters within narrow-to-region.
emulate -L zsh
setopt extendedglob
local lbuffer rbuffer predisplay=$PREDISPLAY postdisplay=$POSTDISPLAY
integer start end swap cursor=$CURSOR mark=$MARK stat
local _ntr_lbuffer _ntr_rbuffer
local _ntr_predisplay=$PREDISPLAY _ntr_postdisplay=$POSTDISPLAY
integer _ntr_start _ntr_end _ntr_swap _ntr_cursor=$CURSOR _ntr_mark=$MARK
integer _ntr_stat
local opt pretext posttext usepretext useposttext nonempty
local _ntr_opt _ntr_pretext _ntr_posttext _ntr_usepretext _ntr_useposttext
local _ntr_nonempty _ntr_save _ntr_restore
while getopts "np:P:" opt; do
case $opt in
(n) nonempty=1
while getopts "np:P:R:S:" _ntr_opt; do
case $_ntr_opt in
(n) _ntr_nonempty=1
;;
(p) pretext=$OPTARG usepretext=1
(p) _ntr_pretext=$OPTARG _ntr_usepretext=1
;;
(P) posttext=$OPTARG useposttext=1
(P) _ntr_posttext=$OPTARG _ntr_useposttext=1
;;
(*) [[ $opt != '?' ]] && print "$0: unhandled option: $opt" >&2
(R) _ntr_restore=$OPTARG
;;
(S) _ntr_save=$OPTARG
;;
(*) [[ $_ntr_opt != '?' ]] && print "$0: unhandled option: $_ntr_opt" >&2
return 1
;;
esac
done
(( OPTIND > 1 )) && shift $(( OPTIND - 1 ))
if (( $# )); then
if (( $# != 2 )); then
zle -M "$0: supply zero or two arguments"
return 1
fi
start=$1
end=$2
else
start=$MARK
end=$CURSOR
fi
if (( start == end )); then
if [[ $_ntr_restore = _ntr_* || $_ntr_save = _ntr_* ]]; then
zle -M "$0: _ntr_ prefix is reserved" >&2
return 1
elif (( start > end )); then
swap=start
start=end
end=swap
fi
(( end++, cursor -= start, mark -= start ))
if [[ -n $_ntr_save || -z $_ntr_restore ]]; then
lbuffer=${BUFFER[1,start]}
if [[ -z $usepretext || ( -n $nonempty && -z $lbuffer ) ]]; then
pretext=$lbuffer
if (( $# )); then
if (( $# != 2 )); then
zle -M "$0: supply zero or two arguments"
return 1
fi
_ntr_start=$1
_ntr_end=$2
else
_ntr_start=$MARK
_ntr_end=$CURSOR
fi
if (( _ntr_start == _ntr_end )); then
return 1
elif (( _ntr_start > _ntr_end )); then
_ntr_swap=_ntr_start
_ntr_start=_ntr_end
_ntr_end=_ntr_swap
fi
(( _ntr_end++, _ntr_cursor -= _ntr_start, _ntr_mark -= _ntr_start ))
_ntr_lbuffer=${BUFFER[1,_ntr_start]}
if [[ -z $_ntr_usepretext || ( -n $_ntr_nonempty && -z $_ntr_lbuffer ) ]]
then
_ntr_pretext=$_ntr_lbuffer
fi
_ntr_rbuffer=${BUFFER[_ntr_end,-1]}
if [[ -z $_ntr_useposttext || ( -n $_ntr_nonempty && -z $_ntr_rbuffer ) ]]
then
_ntr_posttext=$_ntr_rbuffer
fi
PREDISPLAY="$_ntr_predisplay$_ntr_pretext"
POSTDISPLAY="$_ntr_posttext$_ntr_postdisplay"
BUFFER=${BUFFER[_ntr_start+1,_ntr_end-1]}
CURSOR=$_ntr_cursor
MARK=$_ntr_mark
if [[ -n $_ntr_save ]]; then
eval "$_ntr_save=(${(qq)_ntr_predisplay} ${(qq)_ntr_postdisplay}
${(qq)_ntr_lbuffer} ${(qq)_ntr_rbuffer})" || return 1
fi
fi
rbuffer=${BUFFER[end,-1]}
if [[ -z $useposttext || ( -n $nonempty && -z $rbuffer ) ]]; then
posttext=$rbuffer
if [[ -z $_ntr_save && -z $_ntr_restore ]]; then
zle recursive-edit
_ntr_stat=$?
fi
PREDISPLAY="$predisplay$pretext"
POSTDISPLAY="$posttext$postdisplay"
BUFFER=${BUFFER[start+1,end-1]}
CURSOR=$cursor
MARK=$mark
zle recursive-edit
stat=$?
if [[ -n $_ntr_restore || -z $_ntr_save ]]; then
if [[ -n $_ntr_restore ]]; then
if ! eval "_ntr_predisplay=\${${_ntr_restore}[1]}
_ntr_postdisplay=\${${_ntr_restore}[2]}
_ntr_lbuffer=\${${_ntr_restore}[3]}
_ntr_rbuffer=\${${_ntr_restore}[4]}"; then
zle -M Failed.
return 1
fi
fi
PREDISPLAY=$predisplay
POSTDISPLAY=$postdisplay
LBUFFER="$lbuffer$LBUFFER"
RBUFFER="$RBUFFER$rbuffer"
PREDISPLAY=$_ntr_predisplay
POSTDISPLAY=$_ntr_postdisplay
LBUFFER="$_ntr_lbuffer$LBUFFER"
RBUFFER="$RBUFFER$_ntr_rbuffer"
fi
return $stat
return $_ntr_stat