about summary refs log tree commit diff
path: root/Functions/Zle
diff options
context:
space:
mode:
Diffstat (limited to 'Functions/Zle')
-rw-r--r--Functions/Zle/.distfiles3
-rw-r--r--Functions/Zle/history-search-end28
-rw-r--r--Functions/Zle/predict-on64
3 files changed, 94 insertions, 1 deletions
diff --git a/Functions/Zle/.distfiles b/Functions/Zle/.distfiles
index 429c133a0..b7ee01e1f 100644
--- a/Functions/Zle/.distfiles
+++ b/Functions/Zle/.distfiles
@@ -1,3 +1,4 @@
 DISTFILES_SRC='
-    .distfiles incremental-complete-word insert-files
+    .distfiles history-search-end incremental-complete-word insert-files
+    predict-on
 '
diff --git a/Functions/Zle/history-search-end b/Functions/Zle/history-search-end
new file mode 100644
index 000000000..24e7a0a87
--- /dev/null
+++ b/Functions/Zle/history-search-end
@@ -0,0 +1,28 @@
+# function history-search-end {
+#
+# This implements functions like history-beginning-search-{back,for}ward,
+# but takes the cursor to the end of the line after moving in the
+# history, like history-search-{back,for}ward.  To use them:
+#   zle -N history-beginning-search-backward-end history-search-end
+#   zle -N history-beginning-search-forward-end history-search-end
+#   bindkey '...' history-beginning-search-backward-end
+#   bindkey '...' history-beginning-search-forward-end
+
+integer ocursor=$CURSOR
+
+if [[ $LASTWIDGET = history-beginning-search-*-end ]]; then
+  # Last widget called set $hbs_pos.
+  CURSOR=$hbs_pos
+else
+  hbs_pos=$CURSOR
+fi
+
+if zle .${WIDGET%-end}; then
+  # success, go to end of line
+  zle .end-of-line
+else
+  # failure, restore position
+  CURSOR=$ocursor
+  return 1
+fi
+# }
diff --git a/Functions/Zle/predict-on b/Functions/Zle/predict-on
new file mode 100644
index 000000000..07ce0703a
--- /dev/null
+++ b/Functions/Zle/predict-on
@@ -0,0 +1,64 @@
+# This set of functions implements a sort of magic history searching.
+# After predict-on, typing characters causes the editor to look backward
+# in the history for the first line beginning with what you have typed
+# so far.  After predict-off, editing returns to normal for the line found.
+# In fact, you often don't even need to use predict-off, because if the
+# line doesn't match something in the history, adding a key at the end
+# behaves as normal --- though editing in the middle is liable to delete
+# the rest of the line.
+#
+# To use it:
+#   autoload -U predict-on
+#   zle -N predict-on
+#   zle -N predict-off
+#   bindkey '...' predict-on
+#   bindkey '...' predict-off
+# Note that all the functions are defined when you first call type the
+# predict-on key, which means typing the predict-off key before that gives
+# a harmless error message.
+
+predict-on() {
+    zle -N self-insert insert-and-predict
+    zle -N magic-space insert-and-predict
+    zle -N backward-delete-char delete-backward-and-predict
+}
+predict-off() {
+    zle -A .self-insert self-insert
+    zle -A .magic-space magic-space
+    zle -A .backward-delete-char backward-delete-char
+}
+insert-and-predict () {
+  emulate -L zsh
+  if [[ ${RBUFFER[1]} = ${KEYS[-1]} ]]
+  then
+    # same as what's typed, just move on
+    ((++CURSOR))
+  else
+    LBUFFER="$LBUFFER$KEYS"
+    if [[ $LASTWIDGET == (self-insert|magic-space|backward-delete-char) ]]
+    then
+      zle .history-beginning-search-backward || RBUFFER=""
+    fi
+  fi
+  return 0
+}
+delete-backward-and-predict() {
+  emulate -L zsh
+  if [[ -n "$LBUFFER" ]]
+  then
+    # If the last widget was e.g. a motion, then probably the intent is
+    # to actually edit the line, not change the search prefix.
+    if [[ $LASTWIDGET == (self-insert|magic-space|backward-delete-char) ]]
+    then
+      ((--CURSOR))
+      zle .history-beginning-search-forward || RBUFFER=""
+      return 0
+    else
+      # Depending on preference, you might call "predict-off" here,
+      # and also set up forward deletions to turn off prediction.
+      LBUFFER="$LBUFFER[1,-2]"
+    fi
+  fi
+}
+
+[[ -o kshautoload ]] || predict-on "$@"