From: Andreas Gerler Date: Thu, 31 Oct 2019 17:09:31 +0000 (+0100) Subject: update helm X-Git-Url: http://git.bundesbrandschatzamt.de/?a=commitdiff_plain;h=b31e54e948d23ec8a44198cb5bcfbbb48ab82e4f;p=emacsconfig.git update helm --- diff --git a/bba.org b/bba.org index 9c62294d..ffffc0b4 100644 --- a/bba.org +++ b/bba.org @@ -3449,7 +3449,7 @@ Some links you might check out: (if (>= emacs-major-version 24) (progn (add-to-list 'load-path - "~/.emacs.d/elpa/helm-20191031.725") + "~/.emacs.d/elpa/helm-20191031.839") (require 'helm) (helm-mode 1) (global-set-key (kbd "M-y") 'helm-show-kill-ring) diff --git a/elpa/helm-20191031.725/emacs-helm.sh b/elpa/helm-20191031.725/emacs-helm.sh deleted file mode 100755 index 848a72c6..00000000 --- a/elpa/helm-20191031.725/emacs-helm.sh +++ /dev/null @@ -1,219 +0,0 @@ -#!/usr/bin/env sh - - -## Copyright (C) 2012 ~ 2019 Thierry Volpiatto -## -## This program is free software; you can redistribute it and/or modify -## it under the terms of the GNU General Public License as published by -## the Free Software Foundation, either version 3 of the License, or -## (at your option) any later version. -## -## This program is distributed in the hope that it will be useful, -## but WITHOUT ANY WARRANTY; without even the implied warranty of -## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -## GNU General Public License for more details. -## -## You should have received a copy of the GNU General Public License -## along with this program. If not, see . - -## Commentary: -# Preconfigured `emacs -Q' with a basic Helm configuration. - - -# If TEMP env var exists, use it, otherwise declare it. -test -z "$TEMP" && TEMP="/tmp" - -CONF_FILE="$TEMP/helm-cfg.el" -EMACS=emacs -TOOLBARS=-1 -LOAD_PACKAGES= - -usage () { - cat >&1 < $CONF_FILE <\`helm-find-files'\\n\ -;; - \`occur'(M-s o) =>\`helm-occur'\\n\ -;; - \`list-buffers'(C-x C-b) =>\`helm-buffers-list'\\n\ -;; - \`completion-at-point'(M-tab) =>\`helm-lisp-completion-at-point'[1]\\n\ -;; - \`apropos-command'(C-h a) =>\`helm-apropos'\\n\ -;; - \`dabbrev-expand'(M-/) =>\`helm-dabbrev'\\n\ -;; - \`execute-extended-command'(M-x) =>\`helm-M-x'\\n\\n -;; Some other Emacs commands are \"helmized\" by \`helm-mode'.\\n\ -;; [1] Coming with emacs-24.4, \`completion-at-point' is \"helmized\" by \`helm-mode'\\n\ - -;; which provides Helm completion in many places like \`shell-mode'.\\n\ -;; Find context help for most Helm commands with \`C-h m'.\\n\ -;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;\\n\\n")) - -(setq load-path (quote $LOAD_PATH)) -(require 'package) -;; User may be using a non standard \`package-user-dir'. -;; Modify \`package-directory-list' instead of \`package-user-dir' -;; in case the user starts Helm from a non-ELPA installation. -(unless (file-equal-p package-user-dir "~/.emacs.d/elpa") - (add-to-list 'package-directory-list (directory-file-name - (file-name-directory - (directory-file-name default-directory))))) - -(let* ((str-lst "$LOAD_PACKAGES") - (load-packages (and str-lst - (not (string= str-lst "")) - (split-string str-lst ",")))) - (setq package-load-list - (if (equal load-packages '("all")) - '(all) - (append '((helm-core t) (helm t) (async t) (popup t)) - (mapcar (lambda (p) (list (intern p) t)) load-packages))))) - -(package-initialize) -(add-to-list 'load-path (file-name-directory (file-truename "$0"))) -(unless (> $TOOLBARS 0) - (setq default-frame-alist '((vertical-scroll-bars . nil) - (tool-bar-lines . 0) - (menu-bar-lines . 0) - (fullscreen . nil)))) -(blink-cursor-mode -1) -(require 'helm-config) -(helm-mode 1) -(define-key global-map [remap find-file] 'helm-find-files) -(define-key global-map [remap occur] 'helm-occur) -(define-key global-map [remap list-buffers] 'helm-buffers-list) -(define-key global-map [remap dabbrev-expand] 'helm-dabbrev) -(define-key global-map [remap execute-extended-command] 'helm-M-x) -(define-key global-map [remap apropos-command] 'helm-apropos) -(unless (boundp 'completion-in-region-function) - (define-key lisp-interaction-mode-map [remap completion-at-point] 'helm-lisp-completion-at-point) - (define-key emacs-lisp-mode-map [remap completion-at-point] 'helm-lisp-completion-at-point)) -(add-hook 'kill-emacs-hook #'(lambda () (and (file-exists-p "$CONF_FILE") (delete-file "$CONF_FILE")))) -EOF - -$EMACS -Q -l "$CONF_FILE" "$@" diff --git a/elpa/helm-20191031.725/helm-adaptive.el b/elpa/helm-20191031.725/helm-adaptive.el deleted file mode 100644 index 13b6f638..00000000 --- a/elpa/helm-20191031.725/helm-adaptive.el +++ /dev/null @@ -1,278 +0,0 @@ -;;; helm-adaptive.el --- Adaptive Sorting of Candidates. -*- lexical-binding: t -*- - -;; Original Author: Tamas Patrovics - -;; Copyright (C) 2007 Tamas Patrovics -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'cl-lib) -(require 'helm) - - -(defgroup helm-adapt nil - "Adaptative sorting of candidates for Helm." - :group 'helm) - -(defcustom helm-adaptive-history-file - "~/.emacs.d/helm-adaptive-history" - "Path of file where history information is stored. -When nil history is not saved nor restored after emacs restart unless -you save/restore `helm-adaptive-history' with something else like -psession or desktop." - :type 'string - :group 'helm-adapt) - -(defcustom helm-adaptive-history-length 50 - "Maximum number of candidates stored for a source." - :type 'number - :group 'helm-adapt) - -(defcustom helm-adaptive-sort-by-frequent-recent-usage t - "Try to sort on an average of frequent and recent usage when non-nil. - -When nil sort on frequency usage only. - -Only frequency: -When candidate have low frequency, you have to hit on it many times to -make it going up on top. - -Frequency+recent: -Even with a low frequency, candidate go up on top. If a candidate -have a high frequency but it is not used since some time, it goes -down slowly, but as soon you reuse it it go up on top quickly." - :group 'helm-adapt - :type 'boolean) - -;; Internal -(defvar helm-adaptive-done nil - "nil if history information is not yet stored for the current -selection.") - -(defvar helm-adaptive-history nil - "Contains the stored history information. -Format: ((SOURCE-NAME (SELECTED-CANDIDATE (PATTERN . NUMBER-OF-USE) ...) ...) ...)") - -(defconst helm-adaptive-freq-coefficient 5) -(defconst helm-adaptive-recent-coefficient 2) - -(defun helm-adaptive-done-reset () - (setq helm-adaptive-done nil)) - -;;;###autoload -(define-minor-mode helm-adaptive-mode - "Toggle adaptive sorting in all sources." - :group 'helm-adapt - :require 'helm-adaptive - :global t - (if helm-adaptive-mode - (progn - (unless helm-adaptive-history - (helm-adaptive-maybe-load-history)) - (add-hook 'kill-emacs-hook 'helm-adaptive-save-history) - ;; Should run at beginning of `helm-initial-setup'. - (add-hook 'helm-before-initialize-hook 'helm-adaptive-done-reset) - ;; Should run at beginning of `helm-exit-minibuffer'. - (add-hook 'helm-before-action-hook 'helm-adaptive-store-selection) - ;; Should run at beginning of `helm-select-action'. - (add-hook 'helm-select-action-hook 'helm-adaptive-store-selection)) - (helm-adaptive-save-history) - (setq helm-adaptive-history nil) - (remove-hook 'kill-emacs-hook 'helm-adaptive-save-history) - (remove-hook 'helm-before-initialize-hook 'helm-adaptive-done-reset) - (remove-hook 'helm-before-action-hook 'helm-adaptive-store-selection) - (remove-hook 'helm-select-action-hook 'helm-adaptive-store-selection))) - -(defun helm-adapt-use-adaptive-p (&optional source-name) - "Return current source only if it use adaptive history, nil otherwise." - (when helm-adaptive-mode - (let* ((source (or source-name (helm-get-current-source))) - (adapt-source (or (assoc-default 'filtered-candidate-transformer source) - (assoc-default 'candidate-transformer source)))) - (if (listp adapt-source) - (and (memq 'helm-adaptive-sort adapt-source) source) - (and (eq adapt-source 'helm-adaptive-sort) source))))) - -(defun helm-adaptive-store-selection () - "Store history information for the selected candidate." - (unless helm-adaptive-done - (setq helm-adaptive-done t) - (let ((source (helm-adapt-use-adaptive-p))) - (when source - (let* ((source-name (assoc-default 'name source)) - (source-info (or (assoc source-name helm-adaptive-history) - (progn - (push (list source-name) helm-adaptive-history) - (car helm-adaptive-history)))) - (selection (helm-get-selection nil t)) - (selection-info (progn - (setcdr source-info - (cons - (let ((found (assoc selection (cdr source-info)))) - (if (not found) - ;; new entry - (list selection) - ;; move entry to the beginning of the - ;; list, so that it doesn't get - ;; trimmed when the history is - ;; truncated - (setcdr source-info - (delete found (cdr source-info))) - found)) - (cdr source-info))) - (cadr source-info))) - (pattern-info (progn - (setcdr selection-info - (cons - (let ((found (assoc helm-pattern (cdr selection-info)))) - (if (not found) - ;; new entry - (cons helm-pattern 0) - ;; move entry to the beginning of the - ;; list, so if two patterns used the - ;; same number of times then the one - ;; used last appears first in the list - (setcdr selection-info - (delete found (cdr selection-info))) - found)) - (cdr selection-info))) - (cadr selection-info))) - (timestamp-info (helm-aif (assq 'timestamp (cdr selection-info)) - it - (setcdr selection-info (cons (cons 'timestamp 0) (cdr selection-info))) - (cadr selection-info)))) - ;; Increase usage count. - (setcdr pattern-info (1+ (cdr pattern-info))) - ;; Update timestamp. - (setcdr timestamp-info (float-time)) - ;; Truncate history if needed. - (if (> (length (cdr selection-info)) helm-adaptive-history-length) - (setcdr selection-info - (cl-subseq (cdr selection-info) 0 helm-adaptive-history-length)))))))) - -(defun helm-adaptive-maybe-load-history () - "Load `helm-adaptive-history-file' which contain `helm-adaptive-history'. -Returns nil if `helm-adaptive-history-file' doesn't exist." - (when (and helm-adaptive-history-file - (file-readable-p helm-adaptive-history-file)) - (load-file helm-adaptive-history-file))) - -(defun helm-adaptive-save-history (&optional arg) - "Save history information to file given by `helm-adaptive-history-file'." - (interactive "p") - (when helm-adaptive-history-file - (with-temp-buffer - (insert - ";; -*- mode: emacs-lisp -*-\n" - ";; History entries used for helm adaptive display.\n") - (let (print-length print-level) - (prin1 `(setq helm-adaptive-history ',helm-adaptive-history) - (current-buffer))) - (insert ?\n) - (write-region (point-min) (point-max) helm-adaptive-history-file nil - (unless arg 'quiet))))) - -(defun helm-adaptive-sort (candidates source) - "Sort the CANDIDATES for SOURCE by usage frequency. -This is a filtered candidate transformer you can use with the -`filtered-candidate-transformer' attribute." - (let* ((source-name (assoc-default 'name source)) - (source-info (assoc source-name helm-adaptive-history))) - (if source-info - (let ((usage - ;; Loop in the SOURCE entry of `helm-adaptive-history' - ;; and assemble a list containing the (CANDIDATE - ;; . USAGE-COUNT) pairs. - (cl-loop with cf = (if helm-adaptive-sort-by-frequent-recent-usage - helm-adaptive-freq-coefficient 1) - with cr = helm-adaptive-recent-coefficient - for (src-cand . infos) in (cdr source-info) - for count-freq = 0 - for count-rec = - (helm-aif (and helm-adaptive-sort-by-frequent-recent-usage - (assq 'timestamp infos)) - (* cr (+ (float-time) (cdr it))) - 0) - do (cl-loop for (pattern . score) in - (remove (assq 'timestamp infos) infos) - ;; If current pattern is equal to - ;; the previously used one then - ;; this candidate has priority - ;; (that's why its count-freq is - ;; boosted by 10000) and it only - ;; has to compete with other - ;; candidates which were also - ;; selected with the same pattern. - if (equal pattern helm-pattern) - return (setq count-freq (+ 10000 score)) - else do (cl-incf count-freq score)) - and collect (cons src-cand (+ (* count-freq cf) count-rec)) - into results - ;; Sort the list in descending order, so - ;; candidates with highest priority come - ;; first. - finally return - (sort results (lambda (first second) - (> (cdr first) (cdr second))))))) - (if (consp usage) - ;; Put those candidates first which have the highest usage count. - (cl-loop for (cand . _freq) in usage - for info = (or (and (assq 'multiline source) - (replace-regexp-in-string - "\n\\'" "" cand)) - cand) - when (cl-member info candidates - :test 'helm-adaptive-compare) - collect (car it) into sorted - and do (setq candidates - (cl-remove info candidates - :test 'helm-adaptive-compare)) - finally return (append sorted candidates)) - (message "Your `%s' is maybe corrupted or too old, \ -you should reinitialize it with `helm-reset-adaptive-history'" - helm-adaptive-history-file) - (sit-for 1) - candidates)) - ;; if there is no information stored for this source then do nothing - candidates))) - -;;;###autoload -(defun helm-reset-adaptive-history () - "Delete all `helm-adaptive-history' and his file. -Useful when you have a old or corrupted `helm-adaptive-history-file'." - (interactive) - (when (y-or-n-p "Really delete all your `helm-adaptive-history'? ") - (setq helm-adaptive-history nil) - (delete-file helm-adaptive-history-file))) - -(defun helm-adaptive-compare (x y) - "Compare display parts if some of candidates X and Y. - -Arguments X and Y are cons cell in (DISPLAY . REAL) format or atoms." - (equal (if (listp x) (car x) x) - (if (listp y) (car y) y))) - - -(provide 'helm-adaptive) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-adaptive.el ends here diff --git a/elpa/helm-20191031.725/helm-autoloads.el b/elpa/helm-20191031.725/helm-autoloads.el deleted file mode 100644 index df57a075..00000000 --- a/elpa/helm-20191031.725/helm-autoloads.el +++ /dev/null @@ -1,1050 +0,0 @@ -;;; helm-autoloads.el --- automatically extracted autoloads -;; -;;; Code: -(add-to-list 'load-path (directory-file-name (or (file-name-directory #$) (car load-path)))) - -;;;### (autoloads nil "helm-adaptive" "helm-adaptive.el" (23994 46474 -;;;;;; 909643 705000)) -;;; Generated autoloads from helm-adaptive.el - -(defvar helm-adaptive-mode nil "\ -Non-nil if Helm-Adaptive mode is enabled. -See the `helm-adaptive-mode' command -for a description of this minor mode. -Setting this variable directly does not take effect; -either customize it (see the info node `Easy Customization') -or call the function `helm-adaptive-mode'.") - -(custom-autoload 'helm-adaptive-mode "helm-adaptive" nil) - -(autoload 'helm-adaptive-mode "helm-adaptive" "\ -Toggle adaptive sorting in all sources. - -\(fn &optional ARG)" t nil) - -(autoload 'helm-reset-adaptive-history "helm-adaptive" "\ -Delete all `helm-adaptive-history' and his file. -Useful when you have a old or corrupted `helm-adaptive-history-file'. - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-bookmark" "helm-bookmark.el" (23994 46474 -;;;;;; 907610 560000)) -;;; Generated autoloads from helm-bookmark.el - -(autoload 'helm-bookmarks "helm-bookmark" "\ -Preconfigured `helm' for bookmarks. - -\(fn)" t nil) - -(autoload 'helm-filtered-bookmarks "helm-bookmark" "\ -Preconfigured helm for bookmarks (filtered by category). -Optional source `helm-source-bookmark-addressbook' is loaded -only if external addressbook-bookmark package is installed. - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-buffers" "helm-buffers.el" (23994 46474 -;;;;;; 930982 391000)) -;;; Generated autoloads from helm-buffers.el - -(autoload 'helm-buffers-list "helm-buffers" "\ -Preconfigured `helm' to list buffers. - -\(fn)" t nil) - -(autoload 'helm-mini "helm-buffers" "\ -Preconfigured `helm' displaying `helm-mini-default-sources'. - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-color" "helm-color.el" (23994 46474 938638 -;;;;;; 306000)) -;;; Generated autoloads from helm-color.el - -(autoload 'helm-colors "helm-color" "\ -Preconfigured `helm' for color. - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-comint" "helm-comint.el" (23994 46474 -;;;;;; 913679 557000)) -;;; Generated autoloads from helm-comint.el - -(autoload 'helm-comint-prompts "helm-comint" "\ -Pre-configured `helm' to browse the prompts of the current comint buffer. - -\(fn)" t nil) - -(autoload 'helm-comint-prompts-all "helm-comint" "\ -Pre-configured `helm' to browse the prompts of all comint sessions. - -\(fn)" t nil) - -(autoload 'helm-comint-input-ring "helm-comint" "\ -Preconfigured `helm' that provide completion of `comint' history. - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-command" "helm-command.el" (23994 46474 -;;;;;; 924805 444000)) -;;; Generated autoloads from helm-command.el - -(autoload 'helm-M-x "helm-command" "\ -Preconfigured `helm' for Emacs commands. -It is `helm' replacement of regular `M-x' `execute-extended-command'. - -Unlike regular `M-x' emacs vanilla `execute-extended-command' command, -the prefix args if needed, can be passed AFTER starting `helm-M-x'. -When a prefix arg is passed BEFORE starting `helm-M-x', the first `C-u' -while in `helm-M-x' session will disable it. - -You can get help on each command by persistent action. - -\(fn ARG &optional COMMAND-NAME)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-config" "helm-config.el" (23994 46474 -;;;;;; 911721 532000)) -;;; Generated autoloads from helm-config.el - -(autoload 'helm-configuration "helm-config" "\ -Customize `helm'. - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-dabbrev" "helm-dabbrev.el" (23994 46474 -;;;;;; 901745 205000)) -;;; Generated autoloads from helm-dabbrev.el - -(autoload 'helm-dabbrev "helm-dabbrev" "\ -Preconfigured helm for dynamic abbreviations. - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-elisp" "helm-elisp.el" (23994 46474 918696 -;;;;;; 776000)) -;;; Generated autoloads from helm-elisp.el - -(autoload 'helm-lisp-completion-at-point "helm-elisp" "\ -Preconfigured helm for lisp symbol completion at point. - -\(fn)" t nil) - -(autoload 'helm-complete-file-name-at-point "helm-elisp" "\ -Preconfigured helm to complete file name at point. - -\(fn &optional FORCE)" t nil) - -(autoload 'helm-lisp-indent "helm-elisp" "\ - - -\(fn)" t nil) - -(autoload 'helm-lisp-completion-or-file-name-at-point "helm-elisp" "\ -Preconfigured helm to complete lisp symbol or filename at point. -Filename completion happen if string start after or between a double quote. - -\(fn)" t nil) - -(autoload 'helm-apropos "helm-elisp" "\ -Preconfigured helm to describe commands, functions, variables and faces. -In non interactives calls DEFAULT argument should be provided as a string, -i.e the `symbol-name' of any existing symbol. - -\(fn DEFAULT)" t nil) - -(autoload 'helm-manage-advice "helm-elisp" "\ -Preconfigured `helm' to disable/enable function advices. - -\(fn)" t nil) - -(autoload 'helm-locate-library "helm-elisp" "\ -Preconfigured helm to locate elisp libraries. - -\(fn)" t nil) - -(autoload 'helm-timers "helm-elisp" "\ -Preconfigured `helm' for timers. - -\(fn)" t nil) - -(autoload 'helm-complex-command-history "helm-elisp" "\ -Preconfigured helm for complex command history. - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-elisp-package" "helm-elisp-package.el" -;;;;;; (23994 46474 904594 983000)) -;;; Generated autoloads from helm-elisp-package.el - -(autoload 'helm-list-elisp-packages "helm-elisp-package" "\ -Preconfigured helm for listing and handling emacs packages. - -\(fn ARG)" t nil) - -(autoload 'helm-list-elisp-packages-no-fetch "helm-elisp-package" "\ -Preconfigured helm for emacs packages. - -Same as `helm-list-elisp-packages' but don't fetch packages on remote. -Called with a prefix ARG always fetch packages on remote. - -\(fn ARG)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-eshell" "helm-eshell.el" (23994 46474 -;;;;;; 922815 472000)) -;;; Generated autoloads from helm-eshell.el - -(autoload 'helm-esh-pcomplete "helm-eshell" "\ -Preconfigured helm to provide helm completion in eshell. - -\(fn)" t nil) - -(autoload 'helm-eshell-history "helm-eshell" "\ -Preconfigured helm for eshell history. - -\(fn)" t nil) - -(autoload 'helm-eshell-prompts "helm-eshell" "\ -Pre-configured `helm' to browse the prompts of the current Eshell. - -\(fn)" t nil) - -(autoload 'helm-eshell-prompts-all "helm-eshell" "\ -Pre-configured `helm' to browse the prompts of all Eshell sessions. - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-eval" "helm-eval.el" (23994 46474 897705 -;;;;;; 61000)) -;;; Generated autoloads from helm-eval.el - -(autoload 'helm-eval-expression "helm-eval" "\ -Preconfigured helm for `helm-source-evaluation-result'. - -\(fn ARG)" t nil) - -(autoload 'helm-eval-expression-with-eldoc "helm-eval" "\ -Preconfigured helm for `helm-source-evaluation-result' with `eldoc' support. - -\(fn)" t nil) - -(autoload 'helm-calcul-expression "helm-eval" "\ -Preconfigured helm for `helm-source-calculation-result'. - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-external" "helm-external.el" (23994 46474 -;;;;;; 929953 713000)) -;;; Generated autoloads from helm-external.el - -(autoload 'helm-run-external-command "helm-external" "\ -Preconfigured `helm' to run External PROGRAM asyncronously from Emacs. -If program is already running exit with error. -You can set your own list of commands with -`helm-external-commands-list'. - -\(fn PROGRAM)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-files" "helm-files.el" (23994 46474 935042 -;;;;;; 41000)) -;;; Generated autoloads from helm-files.el - -(autoload 'helm-projects-history "helm-files" "\ - - -\(fn ARG)" t nil) - -(autoload 'helm-browse-project "helm-files" "\ -Preconfigured helm to browse projects. -Browse files and see status of project with its vcs. -Only HG and GIT are supported for now. -Fall back to `helm-browse-project-find-files' -if current directory is not under control of one of those vcs. -With a prefix ARG browse files recursively, with two prefix ARG -rebuild the cache. -If the current directory is found in the cache, start -`helm-browse-project-find-files' even with no prefix ARG. -NOTE: The prefix ARG have no effect on the VCS controlled directories. - -Needed dependencies for VCS: - -and -. - -\(fn ARG)" t nil) - -(autoload 'helm-find-files "helm-files" "\ -Preconfigured `helm' for helm implementation of `find-file'. -Called with a prefix arg show history if some. -Don't call it from programs, use `helm-find-files-1' instead. -This is the starting point for nearly all actions you can do on files. - -\(fn ARG)" t nil) - -(autoload 'helm-delete-tramp-connection "helm-files" "\ -Allow deleting tramp connection or marked tramp connections at once. - -This replace `tramp-cleanup-connection' which is partially broken in -emacs < to 25.1.50.1 (See Emacs Bug#24432). - -It allows additionally to delete more than one connection at once. - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-find" "helm-find.el" (23994 46474 927809 -;;;;;; 695000)) -;;; Generated autoloads from helm-find.el - -(autoload 'helm-find "helm-find" "\ -Preconfigured `helm' for the find shell command. - -Recursively find files whose names are matched by all specified -globbing PATTERNs under the current directory using the external -program specified in `find-program' (usually \"find\"). Every -input PATTERN is silently wrapped into two stars: *PATTERN*. - -With prefix argument, prompt for a directory to search. - -When user option `helm-findutils-search-full-path' is non-nil, -match against complete paths, otherwise, against file names -without directory part. - -The (possibly empty) list of globbing PATTERNs can be followed by -the separator \"*\" plus any number of additional arguments that -are passed to \"find\" literally. - -\(fn ARG)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-font" "helm-font.el" (23994 46474 912661 -;;;;;; 5000)) -;;; Generated autoloads from helm-font.el - -(autoload 'helm-select-xfont "helm-font" "\ -Preconfigured `helm' to select Xfont. - -\(fn)" t nil) - -(autoload 'helm-ucs "helm-font" "\ -Preconfigured helm for `ucs-names'. - -Called with a prefix arg force reloading cache. - -\(fn ARG)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-for-files" "helm-for-files.el" (23994 -;;;;;; 46474 899495 112000)) -;;; Generated autoloads from helm-for-files.el - -(autoload 'helm-for-files "helm-for-files" "\ -Preconfigured `helm' for opening files. -Run all sources defined in `helm-for-files-preferred-list'. - -\(fn)" t nil) - -(autoload 'helm-multi-files "helm-for-files" "\ -Preconfigured helm like `helm-for-files' but running locate only on demand. - -Allow toggling back and forth from locate to others sources with -`helm-multi-files-toggle-locate-binding' key. -This avoid launching needlessly locate when what you search is already -found. - -\(fn)" t nil) - -(autoload 'helm-recentf "helm-for-files" "\ -Preconfigured `helm' for `recentf'. - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-grep" "helm-grep.el" (23994 46474 910684 -;;;;;; 361000)) -;;; Generated autoloads from helm-grep.el - -(autoload 'helm-goto-precedent-file "helm-grep" "\ -Go to precedent file in helm grep/etags buffers. - -\(fn)" t nil) - -(autoload 'helm-goto-next-file "helm-grep" "\ -Go to precedent file in helm grep/etags buffers. - -\(fn)" t nil) - -(autoload 'helm-do-grep-ag "helm-grep" "\ -Preconfigured helm for grepping with AG in `default-directory'. -With prefix-arg prompt for type if available with your AG version. - -\(fn ARG)" t nil) - -(autoload 'helm-grep-do-git-grep "helm-grep" "\ -Preconfigured helm for git-grepping `default-directory'. -With a prefix arg ARG git-grep the whole repository. - -\(fn ARG)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-help" "helm-help.el" (23994 46474 908549 -;;;;;; 679000)) -;;; Generated autoloads from helm-help.el - -(autoload 'helm-documentation "helm-help" "\ -Preconfigured Helm for Helm documentation. -With a prefix arg refresh the documentation. - -Find here the documentation of all documented sources. - -\(fn)" t nil) - -(defvar helm-comp-read-mode-line "\\C/\\[helm-cr-empty-string]:Empty \\\\[helm-help]:Help \\[helm-select-action]:Act \\[helm-maybe-exit-minibuffer]/f1/f2/f-n:NthAct \\[helm-toggle-suspend-update]:Tog.suspend \\[helm-customize-group]:Conf") - -(defvar helm-read-file-name-mode-line-string "\\\\[helm-help]:Help C/\\[helm-cr-empty-string]:Empty \\\\[helm-select-action]:Act \\[helm-maybe-exit-minibuffer]/f1/f2/f-n:NthAct \\[helm-toggle-suspend-update]:Tog.suspend \\[helm-customize-group]:Conf" "\ -String displayed in mode-line in `helm-source-find-files'.") - -(defvar helm-top-mode-line "\\\\[helm-help]:Help \\\\[helm-select-action]:Act \\[helm-maybe-exit-minibuffer]/f1/f2/f-n:NthAct \\[helm-toggle-suspend-update]:Tog.suspend \\[helm-customize-group]:Conf") - -;;;*** - -;;;### (autoloads nil "helm-id-utils" "helm-id-utils.el" (23994 46474 -;;;;;; 920660 910000)) -;;; Generated autoloads from helm-id-utils.el - -(autoload 'helm-gid "helm-id-utils" "\ -Preconfigured helm for `gid' command line of `ID-Utils'. -Need A database created with the command `mkid' -above `default-directory'. -Need id-utils as dependency which provide `mkid', `gid' etc... -See . - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-imenu" "helm-imenu.el" (23994 46474 914711 -;;;;;; 260000)) -;;; Generated autoloads from helm-imenu.el - -(autoload 'helm-imenu "helm-imenu" "\ -Preconfigured `helm' for `imenu'. - -\(fn)" t nil) - -(autoload 'helm-imenu-in-all-buffers "helm-imenu" "\ -Preconfigured helm for fetching imenu entries in all buffers with similar mode as current. -A mode is similar as current if it is the same, it is derived i.e `derived-mode-p' -or it have an association in `helm-imenu-all-buffer-assoc'. - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-info" "helm-info.el" (23994 46474 923768 -;;;;;; 966000)) -;;; Generated autoloads from helm-info.el - -(autoload 'helm-info "helm-info" "\ -Preconfigured `helm' for searching Info files' indices. - -With a prefix argument \\[universal-argument], set REFRESH to non-nil. - -Optional parameter REFRESH, when non-nil, reevaluates -`helm-default-info-index-list'. If the variable has been -customized, set it to its saved value. If not, set it to its -standard value. See `custom-reevaluate-setting' for more. - -REFRESH is useful when new Info files are installed. If -`helm-default-info-index-list' has not been customized, the new -Info files are made available. - -\(fn &optional REFRESH)" t nil) - -(autoload 'helm-info-at-point "helm-info" "\ -Preconfigured `helm' for searching info at point. - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-locate" "helm-locate.el" (23994 46474 -;;;;;; 934043 791000)) -;;; Generated autoloads from helm-locate.el - -(autoload 'helm-projects-find-files "helm-locate" "\ -Find files with locate in `helm-locate-project-list'. -With a prefix arg refresh the database in each project. - -\(fn UPDATE)" t nil) - -(autoload 'helm-locate "helm-locate" "\ -Preconfigured `helm' for Locate. -Note: you can add locate options after entering pattern. -See 'man locate' for valid options and also `helm-locate-command'. - -You can specify a local database with prefix argument ARG. -With two prefix arg, refresh the current local db or create it -if it doesn't exists. - -To create a user specific db, use -\"updatedb -l 0 -o db_path -U directory\". -Where db_path is a filename matched by -`helm-locate-db-file-regexp'. - -\(fn ARG)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-man" "helm-man.el" (23994 46474 936635 -;;;;;; 292000)) -;;; Generated autoloads from helm-man.el - -(autoload 'helm-man-woman "helm-man" "\ -Preconfigured `helm' for Man and Woman pages. -With a prefix arg reinitialize the cache. - -\(fn ARG)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-misc" "helm-misc.el" (23994 46474 919678 -;;;;;; 757000)) -;;; Generated autoloads from helm-misc.el - -(autoload 'helm-world-time "helm-misc" "\ -Preconfigured `helm' to show world time. -Default action change TZ environment variable locally to emacs. - -\(fn)" t nil) - -(autoload 'helm-insert-latex-math "helm-misc" "\ -Preconfigured helm for latex math symbols completion. - -\(fn)" t nil) - -(autoload 'helm-ratpoison-commands "helm-misc" "\ -Preconfigured `helm' to execute ratpoison commands. - -\(fn)" t nil) - -(autoload 'helm-stumpwm-commands "helm-misc" "\ -Preconfigured helm for stumpwm commands. - -\(fn)" t nil) - -(autoload 'helm-minibuffer-history "helm-misc" "\ -Preconfigured `helm' for `minibuffer-history'. - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-mode" "helm-mode.el" (23994 46474 928891 -;;;;;; 861000)) -;;; Generated autoloads from helm-mode.el - -(autoload 'helm-comp-read "helm-mode" "\ -Read a string in the minibuffer, with helm completion. - -It is helm `completing-read' equivalent. - -- PROMPT is the prompt name to use. - -- COLLECTION can be a list, vector, obarray or hash-table. - It can be also a function that receives three arguments: - the values string, predicate and t. See `all-completions' for more details. - -Keys description: - -- TEST: A predicate called with one arg i.e candidate. - -- INITIAL-INPUT: Same as input arg in `helm'. - -- PRESELECT: See preselect arg of `helm'. - -- DEFAULT: This option is used only for compatibility with regular - Emacs `completing-read' (Same as DEFAULT arg of `completing-read'). - -- BUFFER: Name of helm-buffer. - -- MUST-MATCH: Candidate selected must be one of COLLECTION. - -- FUZZY: Enable fuzzy matching. - -- REVERSE-HISTORY: When non--nil display history source after current - source completion. - -- REQUIRES-PATTERN: Same as helm attribute, default is 0. - -- HISTORY: A list containing specific history, default is nil. - When it is non--nil, all elements of HISTORY are displayed in - a special source before COLLECTION. - -- INPUT-HISTORY: A symbol. the minibuffer input history will be - stored there, if nil or not provided, `minibuffer-history' - will be used instead. - -- CASE-FOLD: Same as `helm-case-fold-search'. - -- DEL-INPUT: Boolean, when non--nil (default) remove the partial - minibuffer input from HISTORY is present. - -- PERSISTENT-ACTION: A function called with one arg i.e candidate. - -- PERSISTENT-HELP: A string to document PERSISTENT-ACTION. - -- MODE-LINE: A string or list to display in mode line. - Default is `helm-comp-read-mode-line'. - -- KEYMAP: A keymap to use in this `helm-comp-read'. - (the keymap will be shared with history source) - -- NAME: The name related to this local source. - -- HEADER-NAME: A function to alter NAME, see `helm'. - -- EXEC-WHEN-ONLY-ONE: Bound `helm-execute-action-at-once-if-one' - to non--nil. (possibles values are t or nil). - -- VOLATILE: Use volatile attribute. - -- SORT: A predicate to give to `sort' e.g `string-lessp' - Use this only on small data as it is ineficient. - If you want to sort faster add a sort function to - FC-TRANSFORMER. - Note that FUZZY when enabled is already providing a sort function. - -- FC-TRANSFORMER: A `filtered-candidate-transformer' function - or a list of functions. - -- HIST-FC-TRANSFORMER: A `filtered-candidate-transformer' - function for the history source. - -- MARKED-CANDIDATES: If non--nil return candidate or marked candidates as a list. - -- NOMARK: When non--nil don't allow marking candidates. - -- ALISTP: (default is non--nil) See `helm-comp-read-get-candidates'. - -- CANDIDATES-IN-BUFFER: when non--nil use a source build with - `helm-source-in-buffer' which is much faster. - Argument VOLATILE have no effect when CANDIDATES-IN-BUFFER is non--nil. - -- MATCH-PART: Allow matching only one part of candidate. - See match-part documentation in `helm-source'. - -- MATCH-DYNAMIC: See match-dynamic in `helm-source-sync' - It have no effect when used with CANDIDATES-IN-BUFFER. - -- ALLOW-NEST: Allow nesting this `helm-comp-read' in a helm session. - See `helm'. - -- MULTILINE: See multiline in `helm-source'. - -- GROUP: See group in `helm-source'. - -Any prefix args passed during `helm-comp-read' invocation will be recorded -in `helm-current-prefix-arg', otherwise if prefix args were given before -`helm-comp-read' invocation, the value of `current-prefix-arg' will be used. -That's mean you can pass prefix args before or after calling a command -that use `helm-comp-read' See `helm-M-x' for example. - -\(fn PROMPT COLLECTION &key TEST INITIAL-INPUT DEFAULT PRESELECT (BUFFER \"*Helm Completions*\") MUST-MATCH FUZZY REVERSE-HISTORY (REQUIRES-PATTERN 0) HISTORY INPUT-HISTORY (CASE-FOLD helm-comp-read-case-fold-search) (DEL-INPUT t) (PERSISTENT-ACTION nil) (PERSISTENT-HELP \"DoNothing\") (MODE-LINE helm-comp-read-mode-line) HELP-MESSAGE (KEYMAP helm-comp-read-map) (NAME \"Helm Completions\") HEADER-NAME CANDIDATES-IN-BUFFER MATCH-PART MATCH-DYNAMIC EXEC-WHEN-ONLY-ONE QUIT-WHEN-NO-CAND (VOLATILE t) SORT FC-TRANSFORMER HIST-FC-TRANSFORMER MARKED-CANDIDATES NOMARK (ALISTP t) (CANDIDATE-NUMBER-LIMIT helm-candidate-number-limit) MULTILINE ALLOW-NEST (GROUP \\='helm))" nil nil) - -(autoload 'helm-read-file-name "helm-mode" "\ -Read a file name with helm completion. -It is helm `read-file-name' emulation. - -Argument PROMPT is the default prompt to use. - -Keys description: - -- NAME: Source name, default to \"Read File Name\". - -- INITIAL-INPUT: Where to start read file name, default to `default-directory'. - -- BUFFER: `helm-buffer' name default to \"*Helm Completions*\". - -- TEST: A predicate called with one arg 'candidate'. - -- NORET: Allow disabling helm-ff-RET (have no effect if helm-ff-RET - isn't bound to RET). - -- CASE-FOLD: Same as `helm-case-fold-search'. - -- PRESELECT: helm preselection. - -- HISTORY: Display HISTORY in a special source. - -- MUST-MATCH: Can be 'confirm, nil, or t. - -- FUZZY: Enable fuzzy matching when non-nil (Enabled by default). - -- MARKED-CANDIDATES: When non--nil return a list of marked candidates. - -- NOMARK: When non--nil don't allow marking candidates. - -- ALISTP: Don't use `all-completions' in history (take effect only on history). - -- PERSISTENT-ACTION-IF: a persistent if action function. - -- PERSISTENT-HELP: persistent help message. - -- MODE-LINE: A mode line message, default is `helm-read-file-name-mode-line-string'. - -\(fn PROMPT &key (NAME \"Read File Name\") (INITIAL-INPUT default-directory) (BUFFER \"*Helm file completions*\") TEST NORET (CASE-FOLD helm-file-name-case-fold-search) PRESELECT HISTORY MUST-MATCH (FUZZY t) DEFAULT MARKED-CANDIDATES (CANDIDATE-NUMBER-LIMIT helm-ff-candidate-number-limit) NOMARK (ALISTP t) (PERSISTENT-ACTION-IF \\='helm-find-files-persistent-action-if) (PERSISTENT-HELP \"Hit1 Expand Candidate, Hit2 or (C-u) Find file\") (MODE-LINE helm-read-file-name-mode-line-string))" nil nil) - -(defvar helm-mode nil "\ -Non-nil if Helm mode is enabled. -See the `helm-mode' command -for a description of this minor mode. -Setting this variable directly does not take effect; -either customize it (see the info node `Easy Customization') -or call the function `helm-mode'.") - -(custom-autoload 'helm-mode "helm-mode" nil) - -(autoload 'helm-mode "helm-mode" "\ -Toggle generic helm completion. - -All functions in Emacs that use `completing-read' -or `read-file-name' and friends will use helm interface -when this mode is turned on. - -However you can modify this behavior for functions of your choice -with `helm-completing-read-handlers-alist'. - -Also commands using `completion-in-region' will be helmized when -`helm-mode-handle-completion-in-region' is non nil, you can modify -this behavior with `helm-mode-no-completion-in-region-in-modes'. - -Called with a positive arg, turn on unconditionally, with a -negative arg turn off. -You can turn it on with `helm-mode'. - -Some crap emacs functions may not be supported, -e.g `ffap-alternate-file' and maybe others -You can add such functions to `helm-completing-read-handlers-alist' -with a nil value. - -About `ido-mode': -When you are using `helm-mode', DO NOT use `ido-mode', instead if you -want some commands use `ido', add these commands to -`helm-completing-read-handlers-alist' with `ido' as value. - -Note: This mode is incompatible with Emacs23. - -\(fn &optional ARG)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-net" "helm-net.el" (23994 46474 900586 -;;;;;; 803000)) -;;; Generated autoloads from helm-net.el - -(autoload 'helm-browse-url-firefox "helm-net" "\ -Same as `browse-url-firefox' but detach from emacs. - -So when you quit emacs you can keep your firefox session open -and not be prompted to kill firefox process. - -NOTE: Probably not supported on some systems (e.g Windows). - -\(fn URL &optional IGNORE)" t nil) - -(autoload 'helm-browse-url-opera "helm-net" "\ -Browse URL with opera browser and detach from emacs. - -So when you quit emacs you can keep your opera session open -and not be prompted to kill opera process. - -NOTE: Probably not supported on some systems (e.g Windows). - -\(fn URL &optional IGNORE)" t nil) - -(autoload 'helm-browse-url-chromium "helm-net" "\ -Browse URL with google chrome browser. - -\(fn URL &optional IGNORE)" t nil) - -(autoload 'helm-browse-url-uzbl "helm-net" "\ -Browse URL with uzbl browser. - -\(fn URL &optional IGNORE)" t nil) - -(autoload 'helm-browse-url-conkeror "helm-net" "\ -Browse URL with conkeror browser. - -\(fn URL &optional IGNORE)" t nil) - -(autoload 'helm-surfraw "helm-net" "\ -Preconfigured `helm' to search PATTERN with search ENGINE. - -\(fn PATTERN ENGINE)" t nil) - -(autoload 'helm-google-suggest "helm-net" "\ -Preconfigured `helm' for google search with google suggest. - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-occur" "helm-occur.el" (23994 46474 915743 -;;;;;; 393000)) -;;; Generated autoloads from helm-occur.el - -(autoload 'helm-occur "helm-occur" "\ -Preconfigured helm for searching lines matching pattern in `current-buffer'. - -When `helm-source-occur' is member of -`helm-sources-using-default-as-input' which is the default, -symbol at point is searched at startup. - -When a region is marked search only in this region by narrowing. - -To search in multiples buffers start from one of the commands listing -buffers (i.e. a helm command using `helm-source-buffers-list' like -`helm-mini') and use the multi occur buffers action. - -This is the helm implementation that collect lines matching pattern -like vanilla emacs `occur' but have nothing to do with it, the search -engine beeing completely different and also much faster. - -\(fn)" t nil) - -(autoload 'helm-occur-mode "helm-occur" "\ -Major mode to provide actions in helm moccur saved buffer. - -Special commands: -\\{helm-occur-mode-map} - -\(fn)" t nil) - -(autoload 'helm-occur-from-isearch "helm-occur" "\ -Invoke `helm-occur' from isearch. - -To use this bind it to a key in `isearch-mode-map'. - -\(fn)" t nil) - -(autoload 'helm-multi-occur-from-isearch "helm-occur" "\ -Invoke `helm-multi-occur' from isearch. - -With a prefix arg, reverse the behavior of -`helm-moccur-always-search-in-current'. -The prefix arg can be set before calling -`helm-multi-occur-from-isearch' or during the buffer selection. - -To use this bind it to a key in `isearch-mode-map'. - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-regexp" "helm-regexp.el" (23994 46474 -;;;;;; 925788 765000)) -;;; Generated autoloads from helm-regexp.el - -(autoload 'helm-regexp "helm-regexp" "\ -Preconfigured helm to build regexps. -`query-replace-regexp' can be run from there against found regexp. - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-ring" "helm-ring.el" (23994 46474 933072 -;;;;;; 315000)) -;;; Generated autoloads from helm-ring.el - -(autoload 'helm-mark-ring "helm-ring" "\ -Preconfigured `helm' for `helm-source-mark-ring'. - -\(fn)" t nil) - -(autoload 'helm-global-mark-ring "helm-ring" "\ -Preconfigured `helm' for `helm-source-global-mark-ring'. - -\(fn)" t nil) - -(autoload 'helm-all-mark-rings "helm-ring" "\ -Preconfigured `helm' for `helm-source-global-mark-ring' and `helm-source-mark-ring'. - -\(fn)" t nil) - -(autoload 'helm-register "helm-ring" "\ -Preconfigured `helm' for Emacs registers. - -\(fn)" t nil) - -(autoload 'helm-show-kill-ring "helm-ring" "\ -Preconfigured `helm' for `kill-ring'. -It is drop-in replacement of `yank-pop'. - -First call open the kill-ring browser, next calls move to next line. - -\(fn)" t nil) - -(autoload 'helm-execute-kmacro "helm-ring" "\ -Preconfigured helm for keyboard macros. -Define your macros with `f3' and `f4'. -See (info \"(emacs) Keyboard Macros\") for detailed infos. -This command is useful when used with persistent action. - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-semantic" "helm-semantic.el" (23994 46474 -;;;;;; 906574 106000)) -;;; Generated autoloads from helm-semantic.el - -(autoload 'helm-semantic "helm-semantic" "\ -Preconfigured `helm' for `semantic'. -If ARG is supplied, pre-select symbol at point instead of current - -\(fn ARG)" t nil) - -(autoload 'helm-semantic-or-imenu "helm-semantic" "\ -Preconfigured helm for `semantic' or `imenu'. -If ARG is supplied, pre-select symbol at point instead of current -semantic tag in scope. - -If `semantic-mode' is active in the current buffer, then use -semantic for generating tags, otherwise fall back to `imenu'. -Fill in the symbol at point by default. - -\(fn ARG)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-shell" "helm-shell.el" (23994 46474 902705 -;;;;;; 701000)) -;;; Generated autoloads from helm-shell.el - -(defalias 'helm-shell-prompts 'helm-comint-prompts) - -(defalias 'helm-shell-prompts-all 'helm-comint-prompts-all) - -;;;*** - -;;;### (autoloads nil "helm-sys" "helm-sys.el" (23994 46474 932133 -;;;;;; 185000)) -;;; Generated autoloads from helm-sys.el - -(defvar helm-top-poll-mode nil "\ -Non-nil if Helm-Top-Poll mode is enabled. -See the `helm-top-poll-mode' command -for a description of this minor mode. -Setting this variable directly does not take effect; -either customize it (see the info node `Easy Customization') -or call the function `helm-top-poll-mode'.") - -(custom-autoload 'helm-top-poll-mode "helm-sys" nil) - -(autoload 'helm-top-poll-mode "helm-sys" "\ -Refresh automatically helm top buffer once enabled. - -\(fn &optional ARG)" t nil) - -(autoload 'helm-top "helm-sys" "\ -Preconfigured `helm' for top command. - -\(fn)" t nil) - -(autoload 'helm-list-emacs-process "helm-sys" "\ -Preconfigured `helm' for emacs process. - -\(fn)" t nil) - -(autoload 'helm-xrandr-set "helm-sys" "\ -Preconfigured helm for xrandr. - -\(fn)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-tags" "helm-tags.el" (23994 46474 917735 -;;;;;; 145000)) -;;; Generated autoloads from helm-tags.el - -(autoload 'helm-etags-select "helm-tags" "\ -Preconfigured helm for etags. -If called with a prefix argument REINIT -or if any of the tag files have been modified, reinitialize cache. - -This function aggregates three sources of tag files: - - 1) An automatically located file in the parent directories, - by `helm-etags-get-tag-file'. - 2) `tags-file-name', which is commonly set by `find-tag' command. - 3) `tags-table-list' which is commonly set by `visit-tags-table' command. - -\(fn REINIT)" t nil) - -;;;*** - -;;;### (autoloads nil "helm-utils" "helm-utils.el" (23994 46474 905576 -;;;;;; 168000)) -;;; Generated autoloads from helm-utils.el - -(defvar helm-popup-tip-mode nil "\ -Non-nil if Helm-Popup-Tip mode is enabled. -See the `helm-popup-tip-mode' command -for a description of this minor mode. -Setting this variable directly does not take effect; -either customize it (see the info node `Easy Customization') -or call the function `helm-popup-tip-mode'.") - -(custom-autoload 'helm-popup-tip-mode "helm-utils" nil) - -(autoload 'helm-popup-tip-mode "helm-utils" "\ -Show help-echo informations in a popup tip at end of line. - -\(fn &optional ARG)" t nil) - -;;;*** - -;;;### (autoloads nil nil ("helm-easymenu.el" "helm-pkg.el" "helm-types.el" -;;;;;; "helm-x-files.el") (23994 46474 937667 37000)) - -;;;*** - -;; Local Variables: -;; version-control: never -;; no-byte-compile: t -;; no-update-autoloads: t -;; End: -;;; helm-autoloads.el ends here diff --git a/elpa/helm-20191031.725/helm-bookmark.el b/elpa/helm-20191031.725/helm-bookmark.el deleted file mode 100644 index 66f49cbb..00000000 --- a/elpa/helm-20191031.725/helm-bookmark.el +++ /dev/null @@ -1,737 +0,0 @@ -;;; helm-bookmark.el --- Helm for Emacs regular Bookmarks. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: -(require 'cl-lib) -(require 'bookmark) -(require 'helm) -(require 'helm-lib) -(require 'helm-help) -(require 'helm-types) -(require 'helm-utils) -(require 'helm-info) -(require 'helm-adaptive) -(require 'helm-net) - -(declare-function helm-browse-project "helm-files" (arg)) -(declare-function addressbook-bookmark-edit "ext:addressbook-bookmark.el" (bookmark)) - -(defgroup helm-bookmark nil - "Predefined configurations for `helm.el'." - :group 'helm) - -(defcustom helm-bookmark-show-location nil - "Show location of bookmark on display." - :group 'helm-bookmark - :type 'boolean) - -(defcustom helm-bookmark-default-filtered-sources - (append '(helm-source-bookmark-org - helm-source-bookmark-files&dirs - helm-source-bookmark-helm-find-files - helm-source-bookmark-info - helm-source-bookmark-gnus - helm-source-bookmark-man - helm-source-bookmark-images - helm-source-bookmark-w3m) - (list 'helm-source-bookmark-uncategorized - 'helm-source-bookmark-set)) - "List of sources to use in `helm-filtered-bookmarks'." - :group 'helm-bookmark - :type '(repeat (choice symbol))) - - -(defface helm-bookmark-info - '((t (:foreground "green"))) - "Face used for W3m Emacs bookmarks (not w3m bookmarks)." - :group 'helm-bookmark) - -(defface helm-bookmark-w3m - '((t (:foreground "yellow"))) - "Face used for W3m Emacs bookmarks (not w3m bookmarks)." - :group 'helm-bookmark) - -(defface helm-bookmark-gnus - '((t (:foreground "magenta"))) - "Face used for Gnus bookmarks." - :group 'helm-bookmark) - -(defface helm-bookmark-man - '((t (:foreground "Orange4"))) - "Face used for Woman/man bookmarks." - :group 'helm-bookmark) - -(defface helm-bookmark-file - '((t (:foreground "Deepskyblue2"))) - "Face used for file bookmarks." - :group 'helm-bookmark) - -(defface helm-bookmark-file-not-found - '((t (:foreground "Slategray4"))) - "Face used for file bookmarks." - :group 'helm-bookmark) - -(defface helm-bookmark-directory - '((t (:inherit helm-ff-directory))) - "Face used for file bookmarks." - :group 'helm-bookmark) - -(defface helm-bookmark-addressbook - '((t (:foreground "tomato"))) - "Face used for addressbook bookmarks." - :group 'helm-bookmark) - - -(defvar helm-bookmark-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "C-c o") 'helm-bookmark-run-jump-other-window) - (define-key map (kbd "C-c C-o") 'helm-bookmark-run-jump-other-frame) - (define-key map (kbd "C-d") 'helm-bookmark-run-delete) - (define-key map (kbd "C-]") 'helm-bookmark-toggle-filename) - (define-key map (kbd "M-e") 'helm-bookmark-run-edit) - map) - "Generic Keymap for emacs bookmark sources.") - -(defclass helm-source-basic-bookmarks (helm-source-in-buffer helm-type-bookmark) - ((init :initform (lambda () - (bookmark-maybe-load-default-file) - (helm-init-candidates-in-buffer - 'global - (bookmark-all-names)))) - (filtered-candidate-transformer :initform 'helm-bookmark-transformer))) - -(defvar helm-source-bookmarks - (helm-make-source "Bookmarks" 'helm-source-basic-bookmarks) - "See (info \"(emacs)Bookmarks\").") - -(defun helm-bookmark-transformer (candidates _source) - (cl-loop for i in candidates - for loc = (bookmark-location i) - for len = (string-width i) - for trunc = (if (> len bookmark-bmenu-file-column) - (helm-substring i bookmark-bmenu-file-column) - i) - for sep = (make-string (- (+ bookmark-bmenu-file-column 2) - (length trunc)) - ? ) - if helm-bookmark-show-location - collect (cons (concat trunc sep (if (listp loc) (car loc) loc)) i) - else collect i)) - -(defun helm-bookmark-toggle-filename-1 (_candidate) - (let* ((real (helm-get-selection helm-buffer)) - (trunc (if (> (string-width real) bookmark-bmenu-file-column) - (helm-substring real bookmark-bmenu-file-column) - real)) - (loc (bookmark-location real))) - (setq helm-bookmark-show-location (not helm-bookmark-show-location)) - (helm-update (if helm-bookmark-show-location - (concat (regexp-quote trunc) - " +" - (regexp-quote - (if (listp loc) (car loc) loc))) - (regexp-quote real))))) - -(defun helm-bookmark-toggle-filename () - "Toggle bookmark location visibility." - (interactive) - (with-helm-alive-p - (helm-attrset 'toggle-filename - '(helm-bookmark-toggle-filename-1 . never-split)) - (helm-execute-persistent-action 'toggle-filename))) -(put 'helm-bookmark-toggle-filename 'helm-only t) - -(defun helm-bookmark-jump (candidate) - "Jump to bookmark action." - (let ((current-prefix-arg helm-current-prefix-arg) - non-essential) - (bookmark-jump candidate))) - -(defun helm-bookmark-jump-other-frame (candidate) - "Jump to bookmark in other frame action." - (let ((current-prefix-arg helm-current-prefix-arg) - non-essential) - (bookmark-jump candidate 'switch-to-buffer-other-frame))) - -(defun helm-bookmark-jump-other-window (candidate) - "Jump to bookmark in other window action." - (let (non-essential) - (bookmark-jump-other-window candidate))) - - -;;; bookmark-set -;; -(defvar helm-source-bookmark-set - (helm-build-dummy-source "Set Bookmark" - :filtered-candidate-transformer - (lambda (_candidates _source) - (list (or (and (not (string= helm-pattern "")) - helm-pattern) - "Enter a bookmark name to record"))) - :action '(("Set bookmark" . (lambda (candidate) - (if (string= helm-pattern "") - (message "No bookmark name given for record") - (bookmark-set candidate)))))) - "See (info \"(emacs)Bookmarks\").") - - -;;; Predicates -;; -(defconst helm-bookmark--non-file-filename " - no file -" - "Name to use for `filename' entry, for non-file bookmarks.") - -(defun helm-bookmark-gnus-bookmark-p (bookmark) - "Return non-nil if BOOKMARK is a Gnus bookmark. -BOOKMARK is a bookmark name or a bookmark record." - (or (eq (bookmark-get-handler bookmark) 'bmkext-jump-gnus) - (eq (bookmark-get-handler bookmark) 'gnus-summary-bookmark-jump) - (eq (bookmark-get-handler bookmark) 'bookmarkp-jump-gnus))) - -(defun helm-bookmark-w3m-bookmark-p (bookmark) - "Return non-nil if BOOKMARK is a W3m bookmark. -BOOKMARK is a bookmark name or a bookmark record." - (or (eq (bookmark-get-handler bookmark) 'bmkext-jump-w3m) - (eq (bookmark-get-handler bookmark) 'bookmark-w3m-bookmark-jump) - (eq (bookmark-get-handler bookmark) 'bookmarkp-jump-w3m))) - -(defun helm-bookmark-woman-bookmark-p (bookmark) - "Return non-nil if BOOKMARK is a Woman bookmark. -BOOKMARK is a bookmark name or a bookmark record." - (or (eq (bookmark-get-handler bookmark) 'bmkext-jump-woman) - (eq (bookmark-get-handler bookmark) 'woman-bookmark-jump) - (eq (bookmark-get-handler bookmark) 'bookmarkp-jump-woman))) - -(defun helm-bookmark-man-bookmark-p (bookmark) - "Return non-nil if BOOKMARK is a Man bookmark. -BOOKMARK is a bookmark name or a bookmark record." - (or (eq (bookmark-get-handler bookmark) 'bmkext-jump-man) - (eq (bookmark-get-handler bookmark) 'Man-bookmark-jump) - (eq (bookmark-get-handler bookmark) 'bookmarkp-jump-man))) - -(defun helm-bookmark-woman-man-bookmark-p (bookmark) - "Return non-nil if BOOKMARK is a Man or Woman bookmark. -BOOKMARK is a bookmark name or a bookmark record." - (or (helm-bookmark-man-bookmark-p bookmark) - (helm-bookmark-woman-bookmark-p bookmark))) - -(defun helm-bookmark-info-bookmark-p (bookmark) - "Return non-nil if BOOKMARK is an Info bookmark. -BOOKMARK is a bookmark name or a bookmark record." - (eq (bookmark-get-handler bookmark) 'Info-bookmark-jump)) - -(defun helm-bookmark-image-bookmark-p (bookmark) - "Return non-nil if BOOKMARK bookmarks an image file." - (if (stringp bookmark) - (assq 'image-type (assq bookmark bookmark-alist)) - (assq 'image-type bookmark))) - -(defun helm-bookmark-file-p (bookmark) - "Return non-nil if BOOKMARK bookmarks a file or directory. -BOOKMARK is a bookmark name or a bookmark record. -This excludes bookmarks of a more specific kind (Info, Gnus, and W3m)." - (let* ((filename (bookmark-get-filename bookmark)) - (isnonfile (equal filename helm-bookmark--non-file-filename))) - (and filename (not isnonfile) (not (bookmark-get-handler bookmark))))) - -(defun helm-bookmark-org-file-p (bookmark) - (let* ((filename (bookmark-get-filename bookmark))) - (or (string-suffix-p ".org" filename t) - (string-suffix-p ".org_archive" filename t)))) - -(defun helm-bookmark-helm-find-files-p (bookmark) - "Return non-nil if BOOKMARK bookmarks a `helm-find-files' session. -BOOKMARK is a bookmark name or a bookmark record." - (eq (bookmark-get-handler bookmark) 'helm-ff-bookmark-jump)) - -(defun helm-bookmark-addressbook-p (bookmark) - "Return non--nil if BOOKMARK is a contact recorded with addressbook-bookmark. -BOOKMARK is a bookmark name or a bookmark record." - (if (listp bookmark) - (string= (assoc-default 'type bookmark) "addressbook") - (string= (assoc-default - 'type (assoc bookmark bookmark-alist)) "addressbook"))) - -(defun helm-bookmark-uncategorized-bookmark-p (bookmark) - "Return non--nil if BOOKMARK match no known category." - (cl-loop for pred in '(helm-bookmark-org-file-p - helm-bookmark-addressbook-p - helm-bookmark-gnus-bookmark-p - helm-bookmark-w3m-bookmark-p - helm-bookmark-woman-man-bookmark-p - helm-bookmark-info-bookmark-p - helm-bookmark-image-bookmark-p - helm-bookmark-file-p - helm-bookmark-helm-find-files-p - helm-bookmark-addressbook-p) - never (funcall pred bookmark))) - -(defun helm-bookmark-filter-setup-alist (fn) - "Return a filtered `bookmark-alist' sorted alphabetically." - (cl-loop for b in bookmark-alist - for name = (car b) - when (funcall fn b) collect - (propertize name 'location (bookmark-location name)))) - -;;; Bookmark handlers -;; -(defvar w3m-async-exec) -(defun helm-bookmark-jump-w3m (bookmark) - "Jump to W3m bookmark BOOKMARK, setting a new tab. -If `browse-url-browser-function' is set to something else -than `w3m-browse-url' use it." - (require 'helm-net) - (let* ((file (or (bookmark-prop-get bookmark 'filename) - (bookmark-prop-get bookmark 'url))) - (buf (generate-new-buffer-name "*w3m*")) - (w3m-async-exec nil) - ;; If user don't have anymore w3m installed let it browse its - ;; bookmarks with default browser otherwise assume bookmark - ;; have been bookmarked from w3m and use w3m. - (browse-url-browser-function (or (and (fboundp 'w3m-browse-url) - (executable-find "w3m") - 'w3m-browse-url) - browse-url-browser-function)) - (really-use-w3m (equal browse-url-browser-function 'w3m-browse-url))) - (helm-browse-url file really-use-w3m) - (when really-use-w3m - (bookmark-default-handler - `("" (buffer . ,buf) . ,(bookmark-get-bookmark-record bookmark)))))) - -;; All bookmarks recorded with the handler provided with w3m -;; (`bookmark-w3m-bookmark-jump') will use our handler which open -;; the bookmark in a new tab or in an external browser depending -;; on `browse-url-browser-function'. -(defalias 'bookmark-w3m-bookmark-jump 'helm-bookmark-jump-w3m) - -;; Provide compatibility with old handlers provided in external -;; packages bookmark-extensions.el and bookmark+. -(defalias 'bmkext-jump-woman 'woman-bookmark-jump) -(defalias 'bmkext-jump-man 'Man-bookmark-jump) -(defalias 'bmkext-jump-w3m 'helm-bookmark-jump-w3m) -(defalias 'bmkext-jump-gnus 'gnus-summary-bookmark-jump) -(defalias 'bookmarkp-jump-gnus 'gnus-summary-bookmark-jump) -(defalias 'bookmarkp-jump-w3m 'helm-bookmark-jump-w3m) -(defalias 'bookmarkp-jump-woman 'woman-bookmark-jump) -(defalias 'bookmarkp-jump-man 'Man-bookmark-jump) - - -;;;; Filtered bookmark sources -;; -;; -(defclass helm-source-filtered-bookmarks (helm-source-in-buffer helm-type-bookmark) - ((filtered-candidate-transformer - :initform '(helm-adaptive-sort - helm-highlight-bookmark)))) - -;;; W3m bookmarks. -;; -(defun helm-bookmark-w3m-setup-alist () - "Specialized filter function for bookmarks w3m." - (helm-bookmark-filter-setup-alist 'helm-bookmark-w3m-bookmark-p)) - -(defvar helm-source-bookmark-w3m - (helm-make-source "Bookmark W3m" 'helm-source-filtered-bookmarks - :init (lambda () - (bookmark-maybe-load-default-file) - (helm-init-candidates-in-buffer - 'global (helm-bookmark-w3m-setup-alist))))) - -;;; Images -;; -(defun helm-bookmark-images-setup-alist () - "Specialized filter function for images bookmarks." - (helm-bookmark-filter-setup-alist 'helm-bookmark-image-bookmark-p)) - -(defvar helm-source-bookmark-images - (helm-make-source "Bookmark Images" 'helm-source-filtered-bookmarks - :init (lambda () - (bookmark-maybe-load-default-file) - (helm-init-candidates-in-buffer - 'global (helm-bookmark-images-setup-alist))))) - -;;; Woman Man -;; -(defun helm-bookmark-man-setup-alist () - "Specialized filter function for bookmarks w3m." - (helm-bookmark-filter-setup-alist 'helm-bookmark-woman-man-bookmark-p)) - -(defvar helm-source-bookmark-man - (helm-make-source "Bookmark Woman&Man" 'helm-source-filtered-bookmarks - :init (lambda () - (bookmark-maybe-load-default-file) - (helm-init-candidates-in-buffer - 'global (helm-bookmark-man-setup-alist))))) - -;;; Org files -;; -(defun helm-bookmark-org-setup-alist () - "Specialized filter function for Org file bookmarks." - (helm-bookmark-filter-setup-alist 'helm-bookmark-org-file-p)) - -(defvar helm-source-bookmark-org - (helm-make-source " Bookmarked Org files" 'helm-source-filtered-bookmarks - :init (lambda () - (bookmark-maybe-load-default-file) - (helm-init-candidates-in-buffer - 'global (helm-bookmark-org-setup-alist))))) - -;;; Gnus -;; -(defun helm-bookmark-gnus-setup-alist () - "Specialized filter function for bookmarks gnus." - (helm-bookmark-filter-setup-alist 'helm-bookmark-gnus-bookmark-p)) - -(defvar helm-source-bookmark-gnus - (helm-make-source "Bookmark Gnus" 'helm-source-filtered-bookmarks - :init (lambda () - (bookmark-maybe-load-default-file) - (helm-init-candidates-in-buffer - 'global (helm-bookmark-gnus-setup-alist))))) - -;;; Info -;; -(defun helm-bookmark-info-setup-alist () - "Specialized filter function for bookmarks info." - (helm-bookmark-filter-setup-alist 'helm-bookmark-info-bookmark-p)) - -(defvar helm-source-bookmark-info - (helm-make-source "Bookmark Info" 'helm-source-filtered-bookmarks - :init (lambda () - (bookmark-maybe-load-default-file) - (helm-init-candidates-in-buffer - 'global (helm-bookmark-info-setup-alist))))) - -;;; Files and directories -;; -(defun helm-bookmark-local-files-setup-alist () - "Specialized filter function for bookmarks locals files." - (helm-bookmark-filter-setup-alist 'helm-bookmark-file-p)) - -(defvar helm-source-bookmark-files&dirs - (helm-make-source "Bookmark Files&Directories" 'helm-source-filtered-bookmarks - :init (lambda () - (bookmark-maybe-load-default-file) - (helm-init-candidates-in-buffer - 'global (helm-bookmark-local-files-setup-alist))))) - -;;; Helm find files sessions. -;; -(defun helm-bookmark-helm-find-files-setup-alist () - "Specialized filter function for `helm-find-files' bookmarks." - (helm-bookmark-filter-setup-alist 'helm-bookmark-helm-find-files-p)) - -(defun helm-bookmark-browse-project (candidate) - "Run `helm-browse-project' from action." - (with-helm-default-directory - (bookmark-get-filename candidate) - (helm-browse-project nil))) - -(defun helm-bookmark-run-browse-project () - "Run `helm-bookmark-browse-project' from keyboard." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-bookmark-browse-project))) -(put 'helm-bookmark-run-browse-project 'helm-only t) - -(defvar helm-bookmark-find-files-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-bookmark-map) - (define-key map (kbd "C-x C-d") 'helm-bookmark-run-browse-project) - map)) - -(defclass helm-bookmark-override-inheritor (helm-source) ()) - -(defmethod helm--setup-source ((source helm-bookmark-override-inheritor)) - ;; Ensure `helm-source-in-buffer' method is called. - (call-next-method) - (setf (slot-value source 'action) - (helm-append-at-nth - (cl-loop for (name . action) in helm-type-bookmark-actions - unless (memq action '(helm-bookmark-jump-other-frame - helm-bookmark-jump-other-window)) - collect (cons name action)) - '(("Browse project" . helm-bookmark-browse-project)) 1)) - (setf (slot-value source 'keymap) helm-bookmark-find-files-map)) - -(defclass helm-bookmark-find-files-class (helm-source-filtered-bookmarks - helm-bookmark-override-inheritor) - ()) - -(defvar helm-source-bookmark-helm-find-files - (helm-make-source "Bookmark helm-find-files sessions" 'helm-bookmark-find-files-class - :init (lambda () - (bookmark-maybe-load-default-file) - (helm-init-candidates-in-buffer - 'global (helm-bookmark-helm-find-files-setup-alist))) - :persistent-action (lambda (_candidate) (ignore)) - :persistent-help "Do nothing")) - -;;; Uncategorized bookmarks -;; -(defun helm-bookmark-uncategorized-setup-alist () - "Specialized filter function for uncategorized bookmarks." - (helm-bookmark-filter-setup-alist 'helm-bookmark-uncategorized-bookmark-p)) - -(defvar helm-source-bookmark-uncategorized - (helm-make-source "Bookmark uncategorized" 'helm-source-filtered-bookmarks - :init (lambda () - (bookmark-maybe-load-default-file) - (helm-init-candidates-in-buffer - 'global (helm-bookmark-uncategorized-setup-alist))))) - -;;; Transformer -;; - -(defun helm-highlight-bookmark (bookmarks _source) - "Used as `filtered-candidate-transformer' to colorize bookmarks." - (let ((non-essential t)) - (cl-loop for i in bookmarks - for isfile = (bookmark-get-filename i) - for hff = (helm-bookmark-helm-find-files-p i) - for handlerp = (and (fboundp 'bookmark-get-handler) - (bookmark-get-handler i)) - for isw3m = (and (fboundp 'helm-bookmark-w3m-bookmark-p) - (helm-bookmark-w3m-bookmark-p i)) - for isgnus = (and (fboundp 'helm-bookmark-gnus-bookmark-p) - (helm-bookmark-gnus-bookmark-p i)) - for isman = (and (fboundp 'helm-bookmark-man-bookmark-p) ; Man - (helm-bookmark-man-bookmark-p i)) - for iswoman = (and (fboundp 'helm-bookmark-woman-bookmark-p) ; Woman - (helm-bookmark-woman-bookmark-p i)) - for isannotation = (bookmark-get-annotation i) - for isabook = (string= (bookmark-prop-get i 'type) - "addressbook") - for isinfo = (eq handlerp 'Info-bookmark-jump) - for loc = (bookmark-location i) - for len = (string-width i) - for trunc = (if (and helm-bookmark-show-location - (> len bookmark-bmenu-file-column)) - (helm-substring - i bookmark-bmenu-file-column) - i) - ;; Add a * if bookmark have annotation - if (and isannotation (not (string-equal isannotation ""))) - do (setq trunc (concat "*" (if helm-bookmark-show-location trunc i))) - for sep = (and helm-bookmark-show-location - (make-string (- (+ bookmark-bmenu-file-column 2) - (string-width trunc)) - ? )) - for bmk = (cond ( ;; info buffers - isinfo - (propertize trunc 'face 'helm-bookmark-info - 'help-echo isfile)) - ( ;; w3m buffers - isw3m - (propertize trunc 'face 'helm-bookmark-w3m - 'help-echo isfile)) - ( ;; gnus buffers - isgnus - (propertize trunc 'face 'helm-bookmark-gnus - 'help-echo isfile)) - ( ;; Man Woman - (or iswoman isman) - (propertize trunc 'face 'helm-bookmark-man - 'help-echo isfile)) - ( ;; Addressbook - isabook - (propertize trunc 'face 'helm-bookmark-addressbook)) - (;; Directories (helm-find-files) - hff - (if (and (file-remote-p isfile) - (not (file-remote-p isfile nil t))) - (propertize trunc 'face 'helm-bookmark-file-not-found - 'help-echo isfile) - (propertize trunc 'face 'helm-bookmark-directory - 'help-echo isfile))) - ( ;; Directories (dired) - (and isfile - ;; This is needed because `non-essential' - ;; is not working on Emacs-24.2 and the behavior - ;; of tramp seems to have changed since previous - ;; versions (Need to reenter password even if a - ;; first connection have been established, - ;; probably when host is named differently - ;; i.e machine/localhost) - (and (not (file-remote-p isfile)) - (file-directory-p isfile))) - (propertize trunc 'face 'helm-bookmark-directory - 'help-echo isfile)) - ( ;; Non existing files. - (and isfile - ;; Be safe and call `file-exists-p' - ;; only if file is not remote or - ;; remote but connected. - (or (and (file-remote-p isfile) - (not (file-remote-p isfile nil t))) - (not (file-exists-p isfile)))) - (propertize trunc 'face 'helm-bookmark-file-not-found - 'help-echo isfile)) - ( ;; regular files - t - (propertize trunc 'face 'helm-bookmark-file - 'help-echo isfile))) - collect (if helm-bookmark-show-location - (cons (concat bmk sep (if (listp loc) (car loc) loc)) - i) - (cons bmk i))))) - - -;;; Edit/rename/save bookmarks. -;; -;; -(defun helm-bookmark-edit-bookmark (bookmark-name) - "Edit bookmark's name and file name, and maybe save them. -BOOKMARK-NAME is the current (old) name of the bookmark to be renamed." - (let ((bmk (helm-bookmark-get-bookmark-from-name bookmark-name)) - (handler (bookmark-prop-get bookmark-name 'handler))) - (if (eq handler 'addressbook-bookmark-jump) - (addressbook-bookmark-edit - (assoc bmk bookmark-alist)) - (helm-bookmark-edit-bookmark-1 bookmark-name handler)))) - -(defun helm-bookmark-edit-bookmark-1 (bookmark-name handler) - (let* ((helm--reading-passwd-or-string t) - (bookmark-fname (bookmark-get-filename bookmark-name)) - (bookmark-loc (bookmark-prop-get bookmark-name 'location)) - (new-name (read-from-minibuffer "Name: " bookmark-name)) - (new-loc (read-from-minibuffer "FileName or Location: " - (or bookmark-fname - (if (consp bookmark-loc) - (car bookmark-loc) - bookmark-loc)))) - (docid (and (eq handler 'mu4e-bookmark-jump) - (read-number "Docid: " (cdr bookmark-loc))))) - (when docid - (setq new-loc (cons new-loc docid))) - (when (and (not (equal new-name "")) (not (equal new-loc "")) - (y-or-n-p "Save changes? ")) - (if bookmark-fname - (progn - (helm-bookmark-rename bookmark-name new-name 'batch) - (bookmark-set-filename new-name new-loc)) - (bookmark-prop-set - (bookmark-get-bookmark bookmark-name) 'location new-loc) - (helm-bookmark-rename bookmark-name new-name 'batch)) - (helm-bookmark-maybe-save-bookmark) - (list new-name new-loc)))) - -(defun helm-bookmark-maybe-save-bookmark () - "Increment save counter and maybe save `bookmark-alist'." - (setq bookmark-alist-modification-count (1+ bookmark-alist-modification-count)) - (when (bookmark-time-to-save-p) (bookmark-save))) - -(defun helm-bookmark-rename (old &optional new batch) - "Change bookmark's name from OLD to NEW. -Interactively: - If called from the keyboard, then prompt for OLD. - If called from the menubar, select OLD from a menu. -If NEW is nil, then prompt for its string value. - -If BATCH is non-nil, then do not rebuild the menu list. - -While the user enters the new name, repeated `C-w' inserts consecutive -words from the buffer into the new bookmark name." - (interactive (list (bookmark-completing-read "Old bookmark name"))) - (bookmark-maybe-historicize-string old) - (bookmark-maybe-load-default-file) - (save-excursion (skip-chars-forward " ") (setq bookmark-yank-point (point))) - (setq bookmark-current-buffer (current-buffer)) - (let ((newname (or new (read-from-minibuffer - "New name: " nil - (let ((now-map (copy-keymap minibuffer-local-map))) - (define-key now-map "\C-w" 'bookmark-yank-word) - now-map) - nil 'bookmark-history)))) - (bookmark-set-name old newname) - (setq bookmark-current-bookmark newname) - (unless batch (bookmark-bmenu-surreptitiously-rebuild-list)) - (helm-bookmark-maybe-save-bookmark) newname)) - -(defun helm-bookmark-run-edit () - "Run `helm-bookmark-edit-bookmark' from keyboard." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-bookmark-edit-bookmark))) -(put 'helm-bookmark-run-edit 'helm-only t) - - -(defun helm-bookmark-run-jump-other-frame () - "Jump to bookmark other frame from keyboard." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-bookmark-jump-other-frame))) -(put 'helm-bookmark-run-jump-other-frame 'helm-only t) - -(defun helm-bookmark-run-jump-other-window () - "Jump to bookmark from keyboard." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-bookmark-jump-other-window))) -(put 'helm-bookmark-run-jump-other-window 'helm-only t) - -(defun helm-bookmark-run-delete () - "Delete bookmark from keyboard." - (interactive) - (with-helm-alive-p - (when (y-or-n-p "Delete bookmark(s)?") - (helm-exit-and-execute-action 'helm-delete-marked-bookmarks)))) -(put 'helm-bookmark-run-delete 'helm-only t) - -(defun helm-bookmark-get-bookmark-from-name (bmk) - "Return bookmark name even if it is a bookmark with annotation. -e.g prepended with *." - (let ((bookmark (replace-regexp-in-string "\\`\\*" "" bmk))) - (if (assoc bookmark bookmark-alist) bookmark bmk))) - -(defun helm-delete-marked-bookmarks (_ignore) - "Delete this bookmark or all marked bookmarks." - (cl-dolist (i (helm-marked-candidates)) - (bookmark-delete (helm-bookmark-get-bookmark-from-name i) - 'batch))) - - -;;;###autoload -(defun helm-bookmarks () - "Preconfigured `helm' for bookmarks." - (interactive) - (helm :sources '(helm-source-bookmarks - helm-source-bookmark-set) - :buffer "*helm bookmarks*" - :default (buffer-name helm-current-buffer))) - -;;;###autoload -(defun helm-filtered-bookmarks () - "Preconfigured helm for bookmarks (filtered by category). -Optional source `helm-source-bookmark-addressbook' is loaded -only if external addressbook-bookmark package is installed." - (interactive) - (helm :sources helm-bookmark-default-filtered-sources - :prompt "Search Bookmark: " - :buffer "*helm filtered bookmarks*" - :default (list (thing-at-point 'symbol) - (buffer-name helm-current-buffer)))) - -(provide 'helm-bookmark) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-bookmark.el ends here diff --git a/elpa/helm-20191031.725/helm-buffers.el b/elpa/helm-20191031.725/helm-buffers.el deleted file mode 100644 index 1fa450e1..00000000 --- a/elpa/helm-20191031.725/helm-buffers.el +++ /dev/null @@ -1,1152 +0,0 @@ -;;; helm-buffers.el --- helm support for buffers. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'cl-lib) -(require 'helm) -(require 'helm-types) -(require 'helm-utils) -(require 'helm-grep) -(require 'helm-regexp) -(require 'helm-help) -(require 'helm-occur) - -(declare-function ido-make-buffer-list "ido" (default)) -(declare-function ido-add-virtual-buffers-to-list "ido") -(declare-function helm-comp-read "helm-mode") -(declare-function helm-browse-project "helm-files") - - -(defgroup helm-buffers nil - "Buffers related Applications and libraries for Helm." - :group 'helm) - -(defcustom helm-boring-buffer-regexp-list - '("\\` " "\\`\\*helm" "\\`\\*Echo Area" "\\`\\*Minibuf") - "The regexp list that match boring buffers. -Buffer candidates matching these regular expression will be -filtered from the list of candidates if the -`helm-skip-boring-buffers' candidate transformer is used." - :type '(repeat (choice regexp)) - :group 'helm-buffers) - -(defcustom helm-white-buffer-regexp-list nil - "The regexp list of not boring buffers. -These buffers will be displayed even if they match one of -`helm-boring-buffer-regexp-list'." - :type '(repeat (choice regexp)) - :group 'helm-buffers) - -(defcustom helm-buffers-favorite-modes '(lisp-interaction-mode - emacs-lisp-mode - text-mode - org-mode) - "List of preferred mode to open new buffers with." - :type '(repeat (choice function)) - :group 'helm-buffers) - -(defcustom helm-buffer-max-length 20 - "Max length of buffer names before truncate. -When disabled (nil) use the longest buffer-name length found." - :group 'helm-buffers - :type '(choice (const :tag "Disabled" nil) - (integer :tag "Length before truncate"))) - -(defcustom helm-buffer-details-flag t - "Always show details in buffer list when non--nil." - :group 'helm-buffers - :type 'boolean) - -(defcustom helm-buffers-fuzzy-matching nil - "Fuzzy matching buffer names when non--nil. -Only buffer names are fuzzy matched when this is enabled, -`major-mode' matching is not affected by this." - :group 'helm-buffers - :type 'boolean) - -(defcustom helm-buffer-skip-remote-checking nil - "Ignore checking for `file-exists-p' on remote files." - :group 'helm-buffers - :type 'boolean) - -(defcustom helm-buffers-truncate-lines t - "Truncate lines in `helm-buffers-list' when non--nil." - :group 'helm-buffers - :type 'boolean) - -(defcustom helm-buffers-left-margin-width helm-left-margin-width - "`left-margin-width' value for `helm-mini' and `helm-buffers-list'." - :group 'helm-buffers - :type 'integer) - -(defcustom helm-mini-default-sources '(helm-source-buffers-list - helm-source-recentf - helm-source-buffer-not-found) - "Default sources list used in `helm-mini'. - -When adding a source here it is up to you to ensure the library of -this source is accessible and properly loaded." - :group 'helm-buffers - :type '(repeat (choice symbol))) - -(defcustom helm-buffers-end-truncated-string "..." - "The string to display at end of truncated buffer names." - :type 'string - :group 'helm-buffers) - -(defcustom helm-buffers-column-separator " " - "Separator for columns in buffer listing." - :type 'string - :group 'helm-buffers) - -(defcustom helm-buffer--pretty-names '((dired-mode . "Dired") - (lisp-interaction-mode . "Lisp Inter")) - "An alist specifying pretty names for modes. -Most of the time buffer's `mode-name' is a string so no need to add it -here as there is no need to compute it, but sometimes it may be a -mode-line specification which may be costly to compute, in this case -add here the pretty name as a string to avoid this costly computation. -Also if some pretty names are too long you can add your own -abbreviation here." - :type '(alist :key-type symbol :value-type string) - :group 'helm-buffers) - -(defcustom helm-buffers-maybe-switch-to-tab nil - "Switch to buffer in its tab when non nil. -This have no effect when `tab-bar-mode' is not available." - :group 'helm-buffers - :type 'boolean) - - -;;; Faces -;; -;; -(defgroup helm-buffers-faces nil - "Customize the appearance of helm-buffers." - :prefix "helm-" - :group 'helm-buffers - :group 'helm-faces) - -(defface helm-buffer-saved-out - '((t (:foreground "red" :background "black"))) - "Face used for buffer files modified outside of emacs." - :group 'helm-buffers-faces) - -(defface helm-buffer-not-saved - '((t (:foreground "Indianred2"))) - "Face used for buffer files not already saved on disk." - :group 'helm-buffers-faces) - -(defface helm-buffer-modified - '((t :inherit font-lock-comment-face)) - "Face used for modified buffers." - :group 'helm-buffers-faces) - -(defface helm-buffer-size - '((((background dark)) :foreground "RosyBrown") - (((background light)) :foreground "SlateGray")) - "Face used for buffer size." - :group 'helm-buffers-faces) - -(defface helm-buffer-process - '((t (:foreground "Sienna3"))) - "Face used for process status in buffer." - :group 'helm-buffers-faces) - -(defface helm-buffer-directory - '((t (:foreground "DarkRed" :background "LightGray"))) - "Face used for directories in `helm-buffers-list'." - :group 'helm-buffers-faces) - -(defface helm-buffer-file - '((t :inherit font-lock-builtin-face)) - "Face for buffer file names in `helm-buffers-list'." - :group 'helm-buffers-faces) - -(defface helm-buffer-archive - '((t (:foreground "Gold"))) - "Face for archive file names in `helm-buffers-list'." - :group 'helm-buffers-faces) - -(defface helm-non-file-buffer - '((t (:inherit italic))) - "Face used for non-file buffers in `helm-buffers-list'." - :group 'helm-buffers-faces) - -(defvar helm-buffers-tick-counter nil - "Allows recording local changes to a non-file buffer. -Typical usage of this var is for modes that want to see if -their buffers have changed since last visit. -Such programs may want to record tick counter after visiting their -buffers like this: - - (setq helm-buffers-tick-counter (buffer-modified-tick)) - -Note that this variable is buffer-local.") -(make-variable-buffer-local 'helm-buffers-tick-counter) - - -;;; Buffers keymap -;; -(defvar helm-buffer-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - ;; No need to have separate command for grep and zgrep - ;; as we don't use recursivity for buffers. - ;; So use zgrep for both as it is capable to handle non--compressed files. - (define-key map (kbd "M-g s") 'helm-buffer-run-zgrep) - (define-key map (kbd "C-s") 'helm-buffers-run-occur) - (define-key map (kbd "C-x C-d") 'helm-buffers-run-browse-project) - (define-key map (kbd "C-c o") 'helm-buffer-switch-other-window) - (define-key map (kbd "C-c C-o") 'helm-buffer-switch-other-frame) - (define-key map (kbd "C-c =") 'helm-buffer-run-ediff) - (define-key map (kbd "M-=") 'helm-buffer-run-ediff-merge) - (define-key map (kbd "C-=") 'helm-buffer-diff-persistent) - (define-key map (kbd "M-G") 'helm-buffer-revert-persistent) - (define-key map (kbd "C-c d") 'helm-buffer-run-kill-persistent) - (define-key map (kbd "M-D") 'helm-buffer-run-kill-buffers) - (define-key map (kbd "C-x C-s") 'helm-buffer-save-persistent) - (define-key map (kbd "C-x s") 'helm-buffer-run-save-some-buffers) - (define-key map (kbd "C-M-%") 'helm-buffer-run-query-replace-regexp) - (define-key map (kbd "M-%") 'helm-buffer-run-query-replace) - (define-key map (kbd "M-R") 'helm-buffer-run-rename-buffer) - (define-key map (kbd "M-m") 'helm-toggle-all-marks) - (define-key map (kbd "M-a") 'helm-mark-all) - (define-key map (kbd "C-]") 'helm-toggle-buffers-details) - (define-key map (kbd "C-c a") 'helm-buffers-toggle-show-hidden-buffers) - (define-key map (kbd "C-M-SPC") 'helm-buffers-mark-similar-buffers) - (when (fboundp 'tab-bar-mode) - (define-key map (kbd "C-c C-t") 'helm-buffers-switch-to-buffer-new-tab)) - map) - "Keymap for buffer sources in helm.") - -(defvar helm-buffers-ido-virtual-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "C-c o") 'helm-ff-run-switch-other-window) - (define-key map (kbd "C-c C-o") 'helm-ff-run-switch-other-frame) - (define-key map (kbd "M-g s") 'helm-ff-run-grep) - (define-key map (kbd "M-g z") 'helm-ff-run-zgrep) - (define-key map (kbd "M-D") 'helm-ff-run-delete-file) - (define-key map (kbd "C-c C-x") 'helm-ff-run-open-file-externally) - map)) - - -(defvar helm-buffer-max-len-mode nil) -(defvar helm-buffers-in-project-p nil) -(defvar helm-source-buffers-list nil) - -(defun helm-buffers-list--init () - (require 'dired) - ;; Issue #51 Create the list before `helm-buffer' creation. - ;; We were using a global cache in the past and 'candidates was - ;; bound to this cache, this was a problem when using more than one - ;; source with a different 'buffer-list fn as the same cache was - ;; reused in each source (issue #1907), now 'candidates attr is set - ;; directly so that each list of candidates is local to source. - (helm-attrset 'candidates (funcall (helm-attr 'buffer-list))) - (let ((result (cl-loop with allbufs = (memq 'helm-shadow-boring-buffers - (helm-attr - 'filtered-candidate-transformer - helm-source-buffers-list)) - for b in (if allbufs - (helm-attr 'candidates) - (helm-skip-boring-buffers - (helm-attr 'candidates) - helm-source-buffers-list)) - maximize (length b) into len-buf - maximize (length (helm-buffer--format-mode-name b)) - into len-mode - finally return (cons len-buf len-mode)))) - (unless (default-value 'helm-buffer-max-length) - (helm-set-local-variable 'helm-buffer-max-length (car result))) - (unless (default-value 'helm-buffer-max-len-mode) - (helm-set-local-variable 'helm-buffer-max-len-mode (cdr result))))) - -(defclass helm-source-buffers (helm-source-sync helm-type-buffer) - ((buffer-list - :initarg :buffer-list - :initform #'helm-buffer-list - :custom function - :documentation - " A function with no arguments to create buffer list.") - (init :initform 'helm-buffers-list--init) - (multimatch :initform nil) - (match :initform 'helm-buffers-match-function) - (persistent-action :initform 'helm-buffers-list-persistent-action) - (keymap :initform helm-buffer-map) - (migemo :initform 'nomultimatch) - (volatile :initform t) - (nohighlight :initform t) - (resume :initform (lambda () (setq helm-buffers-in-project-p nil))) - (help-message :initform 'helm-buffer-help-message))) - -(cl-defun helm-buffers-create-new-buffer-1 (candidate &optional (display-func 'switch-to-buffer)) - (let ((mjm (or (and helm-current-prefix-arg - (intern-soft (helm-comp-read - "Major-mode: " - helm-buffers-favorite-modes))) - (cl-loop for (r . m) in auto-mode-alist - when (string-match r candidate) - return m))) - (buffer (get-buffer-create candidate))) - (if mjm - (with-current-buffer buffer (funcall mjm)) - (set-buffer-major-mode buffer)) - (funcall display-func buffer))) - -(defun helm-buffers-create-new-buffer (candidate) - (helm-buffers-create-new-buffer-1 candidate)) - -(defun helm-buffers-create-new-buffer-ow (candidate) - (helm-buffers-create-new-buffer-1 candidate 'switch-to-buffer-other-window)) - -(defun helm-buffers-not-found-run-switch-ow () - "Run create new buffer other window action from keymap." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-buffers-create-new-buffer-ow))) -(put 'helm-buffers-not-found-run-switch-ow 'helm-only t) - -(defun helm-buffers-create-new-buffer-of (candidate) - (helm-buffers-create-new-buffer-1 candidate 'switch-to-buffer-other-frame)) - -(defun helm-buffers-not-found-run-switch-of () - "Run create new buffer other frame action from keymap." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-buffers-create-new-buffer-of))) -(put 'helm-buffers-not-found-run-switch-of 'helm-only t) - -(defvar helm-buffer-not-found-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "C-c o") 'helm-buffers-not-found-run-switch-ow) - (define-key map (kbd "C-c C-o") 'helm-buffers-not-found-run-switch-of) - map) - "Keymap for `helm-source-buffer-not-found' source.") - -(defvar helm-source-buffer-not-found - (helm-build-dummy-source - "Create buffer" - :action (helm-make-actions - "Create buffer (C-u choose mode)" - #'helm-buffers-create-new-buffer - "Create buffer other window (C-u choose mode)" - #'helm-buffers-create-new-buffer-ow - "Create buffer other frame (C-u choose mode)" - #'helm-buffers-create-new-buffer-of) - :keymap helm-buffer-not-found-map)) - -(defvar ido-temp-list) -(defvar ido-ignored-list) -(defvar ido-process-ignore-lists) -(defvar ido-use-virtual-buffers) -(defvar ido-virtual-buffers) - -(defvar helm-source-ido-virtual-buffers - (helm-build-sync-source "Ido virtual buffers" - :candidates (lambda () - (let (ido-temp-list - ido-ignored-list - (ido-process-ignore-lists t)) - (when ido-use-virtual-buffers - (ido-add-virtual-buffers-to-list) - ido-virtual-buffers))) - :fuzzy-match helm-buffers-fuzzy-matching - :keymap helm-buffers-ido-virtual-map - :help-message 'helm-buffers-ido-virtual-help-message - :action '(("Find file" . helm-find-many-files) - ("Find file other window" . find-file-other-window) - ("Find file other frame" . find-file-other-frame) - ("Find file as root" . helm-find-file-as-root) - ("Grep File(s) `C-u recurse'" . helm-find-files-grep) - ("Zgrep File(s) `C-u Recurse'" . helm-ff-zgrep) - ("View file" . view-file) - ("Delete file(s)" . helm-delete-marked-files) - ("Open file externally (C-u to choose)" - . helm-open-file-externally)))) - - -(defvar ido-use-virtual-buffers) -(defvar ido-ignore-buffers) -(defun helm-buffer-list () - "Return the current list of buffers. -Currently visible buffers are put at the end of the list. -See `ido-make-buffer-list' for more infos." - (require 'ido) - (let ((ido-process-ignore-lists t) - ido-ignored-list - ido-ignore-buffers - ido-use-virtual-buffers) - (ido-make-buffer-list nil))) - -(defun helm-buffer-size (buffer) - "Return size of BUFFER." - (with-current-buffer buffer - (save-restriction - (widen) - (helm-file-human-size - (- (position-bytes (point-max)) - (position-bytes (point-min))))))) - -(defun helm-buffer--show-details (buf-name prefix help-echo - size mode dir face1 face2 - proc details type) - (append - (list - (concat prefix - (propertize buf-name 'face face1 - 'help-echo help-echo - 'type type))) - (and details - (list size mode - (propertize - (if proc - (format "(%s %s in `%s')" - (process-name proc) - (process-status proc) dir) - (format "(in `%s')" dir)) - 'face face2))))) - -(defun helm-buffer--format-mode-name (buf) - "Prevent using `format-mode-line' as much as possible." - (with-current-buffer buf - (helm-acond ((assq major-mode helm-buffer--pretty-names) - (cdr it)) - ((stringp mode-name) mode-name) - (t (format-mode-line mode-name))))) - -(defun helm-buffer--details (buffer &optional details) - (require 'dired) - (let* ((mode (helm-buffer--format-mode-name buffer)) - (buf (get-buffer buffer)) - (size (propertize (helm-buffer-size buf) - 'face 'helm-buffer-size)) - (proc (get-buffer-process buf)) - (dir (with-current-buffer buffer - (helm-aif default-directory (abbreviate-file-name it)))) - (file-name (helm-aif (buffer-file-name buf) (abbreviate-file-name it))) - (name (buffer-name buf)) - (name-prefix (when (and dir (file-remote-p dir)) - (propertize "@ " 'face 'helm-ff-prefix))) - (archive-p (and (fboundp 'tramp-archive-file-name-p) - (tramp-archive-file-name-p dir)))) - (when name-prefix - ;; Remote tramp buffer names may be hexified, make them more readable. - (setq dir (helm-url-unhex-string dir) - name (helm-url-unhex-string name))) - ;; Handle tramp archive buffers specially. - (if archive-p - (helm-buffer--show-details - name name-prefix file-name size mode dir - 'helm-buffer-archive 'helm-buffer-process nil details 'filebuf) - ;; No fancy things on remote buffers. - (if (and name-prefix helm-buffer-skip-remote-checking) - (helm-buffer--show-details - name name-prefix file-name size mode dir - 'helm-buffer-file 'helm-buffer-process nil details 'filebuf) - (cond - (;; A dired buffer. - (rassoc buf dired-buffers) - (helm-buffer--show-details - name name-prefix dir size mode dir - 'helm-buffer-directory 'helm-buffer-process nil details 'dired)) - ;; A buffer file modified somewhere outside of emacs.=>red - ((and file-name - (file-exists-p file-name) - (not (verify-visited-file-modtime buf))) - (helm-buffer--show-details - name name-prefix file-name size mode dir - 'helm-buffer-saved-out 'helm-buffer-process nil details 'modout)) - ;; A new buffer file not already saved on disk (or a deleted file) .=>indianred2 - ((and file-name (not (file-exists-p file-name))) - (helm-buffer--show-details - name name-prefix file-name size mode dir - 'helm-buffer-not-saved 'helm-buffer-process nil details 'notsaved)) - ;; A buffer file modified and not saved on disk.=>orange - ((and file-name (buffer-modified-p buf)) - (helm-buffer--show-details - name name-prefix file-name size mode dir - 'helm-buffer-modified 'helm-buffer-process nil details 'mod)) - ;; A buffer file not modified and saved on disk.=>green - (file-name - (helm-buffer--show-details - name name-prefix file-name size mode dir - 'helm-buffer-file 'helm-buffer-process nil details 'filebuf)) - ;; A non-file, modified buffer - ((with-current-buffer name - (and helm-buffers-tick-counter - (/= helm-buffers-tick-counter (buffer-modified-tick)))) - (helm-buffer--show-details - name (and proc name-prefix) dir size mode dir - 'helm-buffer-modified 'helm-buffer-process proc details 'nofile-mod)) - ;; Any non--file buffer.=>italic - (t - (helm-buffer--show-details - name (and proc name-prefix) dir size mode dir - 'helm-non-file-buffer 'helm-buffer-process proc details 'nofile))))))) - -(defun helm-highlight-buffers (buffers _source) - "Transformer function to highlight BUFFERS list. -Should be called after others transformers i.e (boring buffers)." - (cl-loop for i in buffers - for (name size mode meta) = (if helm-buffer-details-flag - (helm-buffer--details i 'details) - (helm-buffer--details i)) - for truncbuf = (if (> (string-width name) helm-buffer-max-length) - (helm-substring-by-width - name helm-buffer-max-length - helm-buffers-end-truncated-string) - (concat name - (make-string - (- (+ helm-buffer-max-length - (length - helm-buffers-end-truncated-string)) - (string-width name)) - ? ))) - for len = (length mode) - when (> len helm-buffer-max-len-mode) - do (setq helm-buffer-max-len-mode len) - for fmode = (concat (make-string - (- (max helm-buffer-max-len-mode len) len) ? ) - mode) - ;; The max length of a number should be 1023.9X where X is the - ;; units, this is 7 characters. - for formatted-size = (and size (format "%7s" size)) - collect (let ((helm-pattern (helm-buffers--pattern-sans-filters - (and helm-buffers-fuzzy-matching "")))) - (cons (if helm-buffer-details-flag - (concat - (funcall helm-fuzzy-matching-highlight-fn - truncbuf) - helm-buffers-column-separator - formatted-size - helm-buffers-column-separator - fmode - helm-buffers-column-separator - meta) - (funcall helm-fuzzy-matching-highlight-fn name)) - (get-buffer i))))) - -(defun helm-buffer--get-preselection (buffer) - (let ((bufname (buffer-name buffer))) - (when (and bufname - (file-remote-p (with-current-buffer bufname - default-directory))) - (setq bufname (concat "@ " (helm-url-unhex-string bufname)))) - (concat "^" - (if (and (null helm-buffer-details-flag) - (numberp helm-buffer-max-length) - (> (string-width bufname) - helm-buffer-max-length)) - (regexp-quote - (helm-substring-by-width - bufname helm-buffer-max-length - helm-buffers-end-truncated-string)) - (concat (regexp-quote bufname) - (if helm-buffer-details-flag - "$" "[[:blank:]]+")))))) - -(defun helm-toggle-buffers-details () - (interactive) - (with-helm-alive-p - (let* ((buf (helm-get-selection)) - (preselect (helm-buffer--get-preselection buf))) - (setq helm-buffer-details-flag (not helm-buffer-details-flag)) - (helm-update (lambda () - (helm-awhile (re-search-forward preselect nil t) - (helm-mark-current-line) - (when (equal buf (helm-get-selection)) - (cl-return t)))))))) -(put 'helm-toggle-buffers-details 'helm-only t) - -(defun helm-buffers--pattern-sans-filters (&optional separator) - (cl-loop for p in (helm-mm-split-pattern helm-pattern) - unless (member (substring p 0 1) '("*" "/" "@" "!")) - collect p into lst - finally return (mapconcat 'identity lst (or separator " ")))) - -(defun helm-buffers-sort-transformer (candidates source) - (if (string= helm-pattern "") - candidates - (if helm-buffers-fuzzy-matching - (let ((helm-pattern (helm-buffers--pattern-sans-filters))) - (funcall helm-fuzzy-sort-fn candidates source)) - (sort candidates - (lambda (s1 s2) - (< (string-width s1) (string-width s2))))))) - -(defun helm-buffers-mark-similar-buffers-1 (&optional type) - (with-helm-window - (let* ((src (helm-get-current-source)) - (type (or type - (get-text-property - 0 'type (helm-get-selection nil 'withprop src))))) - (save-excursion - (goto-char (helm-get-previous-header-pos)) - (helm-next-line) - (let* ((next-head (helm-get-next-header-pos)) - (end (and next-head - (save-excursion - (goto-char next-head) - (forward-line -1) - (point)))) - (maxpoint (or end (point-max)))) - (while (< (point) maxpoint) - (helm-mark-current-line) - (let ((cand (helm-get-selection nil 'withprop src))) - (when (and (not (helm-this-visible-mark)) - (eq (get-text-property 0 'type cand) type)) - (helm-make-visible-mark))) - (forward-line 1) (end-of-line)))) - (helm-mark-current-line) - (helm-display-mode-line src t) - (when helm-marked-candidates - (message "%s candidates marked" (length helm-marked-candidates)))))) - -(defun helm-buffers-mark-similar-buffers () - "Mark All buffers that have same property `type' than current. -i.e same color." - (interactive) - (with-helm-alive-p - (let ((marked (helm-marked-candidates))) - (if (and (>= (length marked) 1) - (with-helm-window helm-visible-mark-overlays)) - (helm-unmark-all) - (helm-buffers-mark-similar-buffers-1))))) -(put 'helm-buffers-mark-similar-buffers 'helm-only t) - - -;;; match functions -;; -(defun helm-buffer--match-mjm (pattern mjm) - (when (string-match "\\`\\*" pattern) - (cl-loop with patterns = (split-string (substring pattern 1) ",") - for pat in patterns - if (string-match "\\`!" pat) - collect (string-match (substring pat 1) mjm) into neg - else collect (string-match pat mjm) into pos - finally return - (let ((neg-test (cl-loop for i in neg thereis (numberp i))) - (pos-test (cl-loop for i in pos thereis (numberp i)))) - (or - (and neg (not pos) (not neg-test)) - (and pos pos-test) - (and neg neg-test (not neg-test))))))) - -(defvar helm-buffer--memo-hash (make-hash-table :test 'equal)) -(defun helm-buffer--memo-pattern (pattern) - (or (gethash pattern helm-buffer--memo-hash) - (puthash pattern (helm--mapconcat-pattern pattern) - helm-buffer--memo-hash))) - -(defun helm-buffer--match-pattern (pattern candidate &optional nofuzzy) - (let ((bfn (if (and helm-buffers-fuzzy-matching - (not nofuzzy) - (not helm-migemo-mode) - (not (string-match "\\`\\^" pattern))) - #'helm-buffer--memo-pattern - #'identity)) - (mfn (if helm-migemo-mode - #'helm-mm-migemo-string-match #'string-match))) - (if (string-match "\\`!" pattern) - (not (funcall mfn (funcall bfn (substring pattern 1)) - candidate)) - (funcall mfn (funcall bfn pattern) candidate)))) - -(defun helm-buffers--match-from-mjm (candidate) - (let* ((cand (replace-regexp-in-string "^\\s-\\{1\\}" "" candidate)) - (buf (get-buffer cand)) - (regexp (cl-loop with pattern = helm-pattern - for p in (helm-mm-split-pattern pattern) - when (string-match "\\`\\*" p) - return p))) - (if regexp - (when buf - (with-current-buffer buf - (let ((mjm (symbol-name major-mode))) - (helm-buffer--match-mjm regexp mjm)))) - t))) - -(defun helm-buffers--match-from-pat (candidate) - (let* ((regexp-list (cl-loop with pattern = helm-pattern - for p in (helm-mm-split-pattern pattern) - unless (string-match - "\\`\\(\\*\\|/\\|@\\)" p) - collect p)) - (nofuzzy (cdr regexp-list))) - (if regexp-list - (cl-loop for re in regexp-list - always (helm-buffer--match-pattern re candidate nofuzzy)) - t))) - -(defun helm-buffers--match-from-inside (candidate) - (let* ((cand (replace-regexp-in-string "^\\s-\\{1\\}" "" candidate)) - (buf (get-buffer cand)) - (regexp (cl-loop with pattern = helm-pattern - for p in (helm-mm-split-pattern pattern) - when (string-match "\\`@\\(.*\\)" p) - return (match-string 1 p)))) - (if (and buf regexp) - (with-current-buffer buf - (save-excursion - (goto-char (point-min)) - (if helm-migemo-mode - (helm-mm-migemo-forward regexp nil t) - (re-search-forward regexp nil t)))) - t))) - -(defun helm-buffers--match-from-directory (candidate) - (let* ((cand (replace-regexp-in-string "^\\s-\\{1\\}" "" candidate)) - (buf (get-buffer cand)) - (buf-fname (or (buffer-file-name buf) - (car-safe (rassoc buf dired-buffers)))) - (regexps (cl-loop with pattern = helm-pattern - for p in (helm-mm-split-pattern pattern) - when (string-match "\\`/" p) - collect p))) - (if regexps - (cl-loop for re in regexps - thereis - (and buf-fname - (string-match - (substring re 1) (helm-basedir buf-fname)))) - t))) - -(defun helm-buffers-match-function (candidate) - "Default function to match buffers." - (and (helm-buffers--match-from-pat candidate) - (helm-buffers--match-from-mjm candidate) - (helm-buffers--match-from-inside candidate) - (helm-buffers--match-from-directory candidate))) - - -(defun helm-buffer-query-replace-1 (&optional regexp-flag buffers) - "Query replace in marked buffers. -If REGEXP-FLAG is given use `query-replace-regexp'." - (let ((prompt (if regexp-flag "Query replace regexp" "Query replace")) - (bufs (or buffers (helm-marked-candidates))) - (helm--reading-passwd-or-string t)) - (cl-loop with args = (query-replace-read-args prompt regexp-flag t) - for buf in bufs - do - (save-window-excursion - (switch-to-buffer buf) - (save-excursion - (let ((case-fold-search t)) - (goto-char (point-min)) - (apply #'perform-replace - (list (nth 0 args) (nth 1 args) - t regexp-flag (nth 2 args) nil - multi-query-replace-map)))))))) - -(defun helm-buffer-query-replace-regexp (_candidate) - (helm-buffer-query-replace-1 'regexp)) - -(defun helm-buffer-query-replace (_candidate) - (helm-buffer-query-replace-1)) - -(defun helm-buffer-toggle-diff (candidate) - "Toggle diff buffer CANDIDATE with it's file." - (helm-aif (get-buffer-window "*Diff*" 'visible) - (progn (kill-buffer "*Diff*") - (set-window-buffer it helm-current-buffer)) - (let ((buf (get-buffer candidate))) - (if (buffer-file-name buf) - (diff-buffer-with-file buf) - (user-error "Buffer `%s' is not associated to a file" - (buffer-name buf)))))) - -(defun helm-buffer-diff-persistent () - "Toggle diff buffer without quitting helm." - (interactive) - (with-helm-alive-p - (helm-attrset 'diff-action 'helm-buffer-toggle-diff) - (helm-execute-persistent-action 'diff-action))) -(put 'helm-buffer-diff-persistent 'helm-only t) - -(defun helm-revert-buffer (candidate) - (with-current-buffer candidate - (helm-aif (buffer-file-name) - (and (file-exists-p it) (revert-buffer t t))))) - -(defun helm-revert-marked-buffers (_ignore) - (mapc 'helm-revert-buffer (helm-marked-candidates))) - -(defun helm-buffer-revert-and-update (_candidate) - (with-helm-buffer - (let ((marked (helm-marked-candidates)) - (preselect (helm-buffers--quote-truncated-buffer - (helm-get-selection)))) - (cl-loop for buf in marked do (helm-revert-buffer buf)) - (when helm-marked-candidates (helm-unmark-all)) - (helm-update preselect)))) - -(defun helm-buffer-revert-persistent () - "Revert buffer without quitting helm." - (interactive) - (with-helm-alive-p - (helm-attrset 'revert-action '(helm-buffer-revert-and-update . never-split)) - (helm-execute-persistent-action 'revert-action))) -(put 'helm-buffer-revert-persistent 'helm-only t) - -(defun helm-buffer-save-and-update (_candidate) - (with-helm-buffer - (let ((marked (helm-marked-candidates)) - (preselect (helm-get-selection nil t)) - (enable-recursive-minibuffers t)) - (cl-assert marked nil "No buffers need to be saved") - (cl-loop for buf in marked do - (with-current-buffer (get-buffer buf) - (when (buffer-file-name) (save-buffer)))) - (when helm-marked-candidates (helm-unmark-all)) - (helm-update (regexp-quote preselect))))) - -(defun helm-buffer-save-some-buffers (_candidate) - (helm-buffers-mark-similar-buffers-1 'mod) - (helm-buffer-save-and-update nil)) - -(defun helm-buffer-run-save-some-buffers () - "Save unsaved file buffers without quitting helm." - (interactive) - (with-helm-alive-p - (helm-attrset 'save-some-action '(helm-buffer-save-some-buffers . never-split)) - (helm-execute-persistent-action 'save-some-action))) -(put 'helm-buffer-run-save-some-buffers 'helm-only t) - -(defun helm-buffer-save-persistent () - "Save buffer without quitting helm." - (interactive) - (with-helm-alive-p - (helm-attrset 'save-action '(helm-buffer-save-and-update . never-split)) - (helm-execute-persistent-action 'save-action))) -(put 'helm-buffer-save-persistent 'helm-only t) - -(defun helm-buffers-rename-buffer (candidate) - (with-current-buffer candidate - (rename-buffer (helm-read-string "New name: " (buffer-name)) t))) - -(defun helm-buffer-run-rename-buffer () - "Run rename buffer action from `helm-source-buffers-list'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-buffers-rename-buffer))) -(put 'helm-buffer-run-rename-buffer 'helm-only t) - -(defun helm-buffer-run-kill-persistent () - "Kill buffer without quitting helm." - (interactive) - (with-helm-alive-p - (helm-attrset 'kill-action '(helm-buffers-persistent-kill . never-split)) - (helm-execute-persistent-action 'kill-action))) -(put 'helm-buffer-run-kill-persistent 'helm-only t) - -(defun helm-kill-marked-buffers (_ignore) - (let* ((bufs (helm-marked-candidates)) - (killed-bufs (cl-count-if 'kill-buffer bufs))) - (when (buffer-live-p helm-buffer) - (with-helm-buffer - (setq helm-marked-candidates nil - helm-visible-mark-overlays nil))) - (message "Killed %s buffer(s)" killed-bufs))) - -(defun helm-buffer-run-kill-buffers () - "Run kill buffer action from `helm-source-buffers-list'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-kill-marked-buffers))) -(put 'helm-buffer-run-kill-buffers 'helm-only t) - -(defun helm-buffer-run-grep () - "Run Grep action from `helm-source-buffers-list'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-grep-buffers))) -(put 'helm-buffer-run-grep 'helm-only t) - -(defun helm-buffer-run-zgrep () - "Run Grep action from `helm-source-buffers-list'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-zgrep-buffers))) -(put 'helm-buffer-run-zgrep 'helm-only t) - -(defun helm-buffer-run-query-replace-regexp () - "Run Query replace regexp action from `helm-source-buffers-list'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-buffer-query-replace-regexp))) -(put 'helm-buffer-run-query-replace-regexp 'helm-only t) - -(defun helm-buffer-run-query-replace () - "Run Query replace action from `helm-source-buffers-list'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-buffer-query-replace))) -(put 'helm-buffer-run-query-replace 'helm-only t) - -(defun helm-buffer-switch-other-window () - "Run switch to other window action from `helm-source-buffers-list'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-buffer-switch-buffers-other-window))) -(put 'helm-buffer-switch-other-window 'helm-only t) - -(defun helm-buffer-switch-other-frame () - "Run switch to other frame action from `helm-source-buffers-list'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'switch-to-buffer-other-frame))) -(put 'helm-buffer-switch-other-frame 'helm-only t) - -(defun helm-buffers-switch-to-buffer-new-tab () - "Run switch to buffer in other tab action from `helm-source-buffers-list'." - (interactive) - (cl-assert (fboundp 'tab-bar-mode) nil "Tab-bar-mode not available") - (with-helm-alive-p - (helm-exit-and-execute-action 'switch-to-buffer-other-tab))) -(put 'helm-buffers-switch-to-buffer-new-tab 'helm-only t) - -(defun helm-buffer-switch-buffers (_candidate) - "Switch to buffer candidates and replace current buffer. - -If more than one buffer marked switch to these buffers in separate windows. -If a prefix arg is given split windows vertically." - (let ((buffers (helm-marked-candidates))) - (helm-window-show-buffers buffers))) - -(defun helm-buffer-switch-buffers-other-window (_candidate) - "Switch to marked buffers in other windows." - (let ((buffers (helm-marked-candidates))) - (helm-window-show-buffers buffers t))) - -(defun helm-buffer-run-ediff () - "Run ediff action from `helm-source-buffers-list'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-ediff-marked-buffers))) -(put 'helm-buffer-run-ediff 'helm-only t) - -(defun helm-buffer-run-ediff-merge () - "Run ediff action from `helm-source-buffers-list'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-ediff-marked-buffers-merge))) -(put 'helm-buffer-run-ediff-merge 'helm-only t) - -(defun helm-buffers-persistent-kill-1 (buffer-or-name) - "Persistent action to kill buffer." - (let ((buf (get-buffer buffer-or-name)) helm-buf-or-cur) - (if (or (and (eql buf (get-buffer helm-current-buffer)) - (setq helm-buf-or-cur "helm-current-buffer")) - (and (eql buf (get-buffer helm-buffer)) - (setq helm-buf-or-cur "helm-buffer"))) - (progn - (message "Can't kill `%s' without quitting session" helm-buf-or-cur) - (sit-for 1)) - (kill-buffer buf) - (helm-delete-current-selection)))) - -(defun helm-buffers--quote-truncated-buffer (buffer) - (let ((bufname (and (bufferp buffer) - (buffer-name buffer)))) - (when (and bufname - (file-remote-p (with-current-buffer bufname - default-directory))) - (setq bufname (concat "@ " (helm-url-unhex-string bufname)))) - (when bufname - (regexp-quote - (if (and helm-buffer-max-length - helm-buffer-details-flag) - (helm-substring-by-width - bufname helm-buffer-max-length - "") - bufname))))) - -(defun helm-buffers-persistent-kill (_buffer) - (let ((marked (helm-marked-candidates)) - (sel (helm-get-selection))) - (unwind-protect - (cl-loop for b in marked - do (progn - ;; We need to preselect each marked because - ;; helm-buffers-persistent-kill is deleting - ;; current selection. - (helm-preselect - (format "^%s" - (helm-buffers--quote-truncated-buffer b))) - (helm-buffers-persistent-kill-1 b) - (message nil) - (helm--remove-marked-and-update-mode-line b))) - (with-helm-buffer - (setq helm-marked-candidates nil - helm-visible-mark-overlays nil)) - (helm-force-update (helm-buffers--quote-truncated-buffer sel))))) - -(defun helm-buffers-list-persistent-action (candidate) - (let ((current (window-buffer helm-persistent-action-display-window))) - (if (or (helm-follow-mode-p) - (eql current (get-buffer helm-current-buffer)) - (not (eql current (get-buffer candidate)))) - (switch-to-buffer candidate) - (if (and helm-persistent-action-display-window - (window-dedicated-p - (next-window helm-persistent-action-display-window 1))) - (delete-window helm-persistent-action-display-window) - (switch-to-buffer helm-current-buffer))))) - -(defun helm-ediff-marked-buffers (_candidate &optional merge) - "Ediff 2 marked buffers or CANDIDATE and `helm-current-buffer'. -With optional arg MERGE call `ediff-merge-buffers'." - (let ((lg-lst (length (helm-marked-candidates))) - buf1 buf2) - (cl-case lg-lst - (0 - (error "Error:You have to mark at least 1 buffer")) - (1 - (setq buf1 helm-current-buffer - buf2 (cl-first (helm-marked-candidates)))) - (2 - (setq buf1 (cl-first (helm-marked-candidates)) - buf2 (cl-second (helm-marked-candidates)))) - (t - (error "Error:Too many buffers marked!"))) - (if merge - (ediff-merge-buffers buf1 buf2) - (ediff-buffers buf1 buf2)))) - -(defun helm-ediff-marked-buffers-merge (candidate) - "Ediff merge `helm-current-buffer' with CANDIDATE. -See `helm-ediff-marked-buffers'." - (helm-ediff-marked-buffers candidate t)) - -(defun helm-multi-occur-as-action (_candidate) - "Multi occur action for `helm-source-buffers-list'. -Can be used by any source that list buffers." - (let ((helm-occur-always-search-in-current - (if helm-current-prefix-arg - (not helm-occur-always-search-in-current) - helm-occur-always-search-in-current)) - (buffers (helm-marked-candidates)) - (input (cl-loop for i in (split-string (or (buffer-local-value - 'helm-input-local - (get-buffer helm-buffer)) - helm-pattern) - " " t) - thereis (and (string-match "\\`@\\(.*\\)" i) - (match-string 1 i))))) - (helm-multi-occur-1 buffers input))) - -(defun helm-buffers-run-occur () - "Run `helm-multi-occur-as-action' by key." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-multi-occur-as-action))) -(put 'helm-buffers-run-occur 'helm-only t) - -(defun helm-buffers-toggle-show-hidden-buffers () - (interactive) - (with-helm-alive-p - (let ((filter-attrs (helm-attr 'filtered-candidate-transformer - helm-source-buffers-list))) - (if (memq 'helm-shadow-boring-buffers filter-attrs) - (helm-attrset 'filtered-candidate-transformer - (cons 'helm-skip-boring-buffers - (remove 'helm-shadow-boring-buffers - filter-attrs)) - helm-source-buffers-list) - (helm-attrset 'filtered-candidate-transformer - (cons 'helm-shadow-boring-buffers - (remove 'helm-skip-boring-buffers - filter-attrs)) - helm-source-buffers-list)) - (helm-force-update)))) -(put 'helm-buffers-toggle-show-hidden-buffers 'helm-only t) - -(defun helm-buffers-browse-project (buf) - "Browse project from buffer." - (with-current-buffer buf - (helm-browse-project helm-current-prefix-arg))) - -(defun helm-buffers-run-browse-project () - "Run `helm-buffers-browse-project' from key." - (interactive) - (with-helm-alive-p - (if helm-buffers-in-project-p - (user-error "You are already browsing this project") - (helm-exit-and-execute-action 'helm-buffers-browse-project)))) - -;;; Candidate Transformers -;; -;; -(defun helm-skip-boring-buffers (buffers _source) - (helm-skip-entries buffers - helm-boring-buffer-regexp-list - helm-white-buffer-regexp-list)) - -(defun helm-shadow-boring-buffers (buffers _source) - "Buffers matching `helm-boring-buffer-regexp' will be -displayed with the `file-name-shadow' face if available." - (helm-shadow-entries buffers helm-boring-buffer-regexp-list)) - - -;;;###autoload -(defun helm-buffers-list () - "Preconfigured `helm' to list buffers." - (interactive) - (unless helm-source-buffers-list - (setq helm-source-buffers-list - (helm-make-source "Buffers" 'helm-source-buffers))) - (helm :sources '(helm-source-buffers-list - helm-source-ido-virtual-buffers - helm-source-buffer-not-found) - :buffer "*helm buffers*" - :keymap helm-buffer-map - :truncate-lines helm-buffers-truncate-lines - :left-margin-width helm-buffers-left-margin-width)) - -;;;###autoload -(defun helm-mini () - "Preconfigured `helm' displaying `helm-mini-default-sources'." - (interactive) - (require 'helm-x-files) - (unless helm-source-buffers-list - (setq helm-source-buffers-list - (helm-make-source "Buffers" 'helm-source-buffers))) - (helm :sources helm-mini-default-sources - :buffer "*helm mini*" - :ff-transformer-show-only-basename nil - :truncate-lines helm-buffers-truncate-lines - :left-margin-width helm-buffers-left-margin-width)) - -(defun helm-quit-and-helm-mini () - "Drop into `helm-mini' from `helm'." - (interactive) - (with-helm-alive-p - (helm-run-after-exit 'helm-mini))) - -(provide 'helm-buffers) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-buffers.el ends here diff --git a/elpa/helm-20191031.725/helm-color.el b/elpa/helm-20191031.725/helm-color.el deleted file mode 100644 index a962796a..00000000 --- a/elpa/helm-20191031.725/helm-color.el +++ /dev/null @@ -1,170 +0,0 @@ -;;; helm-color.el --- colors and faces -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: -(require 'cl-lib) -(require 'helm) -(require 'helm-help) -(require 'helm-elisp) - -;;; Customize Face -;; -;; -(defun helm-custom-faces-init () - "Initialize buffer for `helm-source-customize-face'." - (unless (helm-candidate-buffer) - (save-selected-window - (list-faces-display) - (message nil)) - (helm-init-candidates-in-buffer - 'global - (with-current-buffer (get-buffer "*Faces*") - (buffer-substring - (next-single-char-property-change (point-min) 'face) - (point-max)))) - (kill-buffer "*Faces*"))) - -(defvar helm-source-customize-face - (helm-build-in-buffer-source "Customize Face" - :init 'helm-custom-faces-init - :get-line 'buffer-substring - :persistent-action (lambda (candidate) - (helm-elisp--persistent-help - (intern (car (split-string candidate))) - 'helm-describe-face)) - :persistent-help "Describe face" - :action '(("Customize" - . (lambda (line) - (customize-face (intern (car (split-string line)))))) - ("Copy name" - . (lambda (line) - (kill-new (car (split-string line " " t))))))) - "See (info \"(emacs)Faces\")") - -;;; Colors browser -;; -;; -(defun helm-colors-init () - (unless (helm-candidate-buffer) - (save-selected-window - (list-colors-display) - (message nil)) - (helm-init-candidates-in-buffer - 'global - (with-current-buffer (get-buffer "*Colors*") - (buffer-string))) - (kill-buffer "*Colors*"))) - -(defun helm-color-insert-name (candidate) - (with-helm-current-buffer - (insert (helm-colors-get-name candidate)))) - -(defun helm-color-kill-name (candidate) - (kill-new (helm-colors-get-name candidate))) - -(defun helm-color-insert-rgb (candidate) - (with-helm-current-buffer - (insert (helm-colors-get-rgb candidate)))) - -(defun helm-color-kill-rgb (candidate) - (kill-new (helm-colors-get-rgb candidate))) - -(defun helm-color-run-insert-name () - "Insert name of color from `helm-source-colors'" - (interactive) - (with-helm-alive-p (helm-exit-and-execute-action 'helm-color-insert-name))) -(put 'helm-color-run-insert-name 'helm-only t) - -(defun helm-color-run-kill-name () - "Kill name of color from `helm-source-colors'" - (interactive) - (with-helm-alive-p (helm-exit-and-execute-action 'helm-color-kill-name))) -(put 'helm-color-run-kill-name 'helm-only t) - -(defun helm-color-run-insert-rgb () - "Insert RGB of color from `helm-source-colors'" - (interactive) - (with-helm-alive-p (helm-exit-and-execute-action 'helm-color-insert-rgb))) -(put 'helm-color-run-insert-rgb 'helm-only t) - -(defun helm-color-run-kill-rgb () - "Kill RGB of color from `helm-source-colors'" - (interactive) - (with-helm-alive-p (helm-exit-and-execute-action 'helm-color-kill-rgb))) -(put 'helm-color-run-kill-rgb 'helm-only t) - -(defvar helm-color-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "C-c n") 'helm-color-run-insert-name) - (define-key map (kbd "C-c N") 'helm-color-run-kill-name) - (define-key map (kbd "C-c r") 'helm-color-run-insert-rgb) - (define-key map (kbd "C-c R") 'helm-color-run-kill-rgb) - map)) - -(defvar helm-source-colors - (helm-build-in-buffer-source "Colors" - :init 'helm-colors-init - :get-line 'buffer-substring - :keymap helm-color-map - :persistent-help "Kill entry in RGB format." - :persistent-action 'helm-color-kill-rgb - :help-message 'helm-colors-help-message - :action - '(("Copy Name (C-c N)" . helm-color-kill-name) - ("Copy RGB (C-c R)" . helm-color-kill-rgb) - ("Insert Name (C-c n)" . helm-color-insert-name) - ("Insert RGB (C-c r)" . helm-color-insert-rgb)))) - -(defun helm-colors-get-name (candidate) - "Get color name." - (replace-regexp-in-string - " " "" - (with-temp-buffer - (insert (capitalize candidate)) - (goto-char (point-min)) - (search-forward-regexp "\\s-\\{2,\\}") - (delete-region (point) (point-max)) - (buffer-string)))) - -(defun helm-colors-get-rgb (candidate) - "Get color RGB." - (replace-regexp-in-string - " " "" - (with-temp-buffer - (insert (capitalize candidate)) - (goto-char (point-max)) - (search-backward-regexp "\\s-\\{2,\\}") - (delete-region (point) (point-min)) - (buffer-string)))) - -;;;###autoload -(defun helm-colors () - "Preconfigured `helm' for color." - (interactive) - (helm :sources '(helm-source-colors helm-source-customize-face) - :buffer "*helm colors*")) - -(provide 'helm-color) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-color.el ends here diff --git a/elpa/helm-20191031.725/helm-comint.el b/elpa/helm-20191031.725/helm-comint.el deleted file mode 100644 index 953d8a76..00000000 --- a/elpa/helm-20191031.725/helm-comint.el +++ /dev/null @@ -1,219 +0,0 @@ -;;; helm-comint.el --- Comint prompt navigation for helm. -*- lexical-binding: t -*- - -;; Copyright (C) 2019 Pierre Neidhardt - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Commentary: -;; -;; You can bind this as follows in .emacs: -;; -;; (add-hook 'comint-mode-hook -;; (lambda () -;; (define-key comint-mode-map (kbd "M-s f") 'helm-comint-prompts-all))) - -;;; Code: -(require 'cl-lib) -(require 'helm) -(require 'helm-lib) -(require 'helm-help) -(require 'helm-elisp) - -;;; Comint prompts -;; -(defface helm-comint-prompts-promptidx - '((t (:foreground "cyan"))) - "Face used to highlight comint prompt index." - :group 'helm-comint-faces) - -(defface helm-comint-prompts-buffer-name - '((t (:foreground "green"))) - "Face used to highlight comint buffer name." - :group 'helm-comint-faces) - -(defcustom helm-comint-prompts-promptidx-p t - "Show prompt number." - :group 'helm-comint - :type 'boolean) - -(defcustom helm-comint-mode-list '(comint-mode slime-repl-mode) - "Supported modes for prompt navigation. -Derived modes (e.g. Geiser's REPL) are automatically supported." - :group 'helm-comint - :type '(repeat (choice symbol))) - -(defcustom helm-comint-max-offset 400 - "Max number of chars displayed per candidate in comint-input-ring browser. -When `t', don't truncate candidate, show all. -By default it is approximatively the number of bits contained in five lines -of 80 chars each i.e 80*5. -Note that if you set this to nil multiline will be disabled, i.e you -will not have anymore separators between candidates." - :type '(choice (const :tag "Disabled" t) - (integer :tag "Max candidate offset")) - :group 'helm-misc) - -(defvar helm-comint-prompts-keymap - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "C-c o") 'helm-comint-prompts-other-window) - (define-key map (kbd "C-c C-o") 'helm-comint-prompts-other-frame) - map) - "Keymap for `helm-comint-prompt-all'.") - -(defun helm-comint-prompts-list (mode &optional buffer) - "List the prompts in BUFFER in mode MODE. - -Return a list of (\"prompt\" (point) (buffer-name) prompt-index)) -e.g. (\"ls\" 162 \"*shell*\" 3). -If BUFFER is nil, use current buffer." - (with-current-buffer (or buffer (current-buffer)) - (when (derived-mode-p mode) - (save-excursion - (goto-char (point-min)) - (let (result (count 1)) - (save-mark-and-excursion - (helm-awhile (and (not (eobp)) (comint-next-prompt 1)) - (push (list (buffer-substring-no-properties - it (point-at-eol)) - it (buffer-name) count) - result) - (setq count (1+ count)))) - (nreverse result)))))) - -(defun helm-comint-prompts-list-all (mode) - "List the prompts of all buffers in mode MODE. -See `helm-comint-prompts-list'." - (cl-loop for b in (buffer-list) - append (helm-comint-prompts-list mode b))) - -(defun helm-comint-prompts-transformer (candidates &optional all) - ;; ("ls" 162 "*shell*" 3) => ("*shell*:3:ls" . ("ls" 162 "*shell*" 3)) - (cl-loop for (prt pos buf id) in candidates - collect `(,(concat - (when all - (concat (propertize - buf - 'face 'helm-comint-prompts-buffer-name) - ":")) - (when helm-comint-prompts-promptidx-p - (concat (propertize - (number-to-string id) - 'face 'helm-comint-prompts-promptidx) - ":")) - prt) - . ,(list prt pos buf id)))) - -(defun helm-comint-prompts-all-transformer (candidates) - (helm-comint-prompts-transformer candidates t)) - -(cl-defun helm-comint-prompts-goto (candidate &optional (action 'switch-to-buffer)) - ;; Candidate format: ("ls" 162 "*shell*" 3) - (let ((buf (nth 2 candidate))) - (unless (and (string= (buffer-name) buf) - (eq action 'switch-to-buffer)) - (funcall action buf)) - (goto-char (nth 1 candidate)) - (recenter))) - -(defun helm-comint-prompts-goto-other-window (candidate) - (helm-comint-prompts-goto candidate 'switch-to-buffer-other-window)) - -(defun helm-comint-prompts-goto-other-frame (candidate) - (helm-comint-prompts-goto candidate 'switch-to-buffer-other-frame)) - -(defun helm-comint-prompts-other-window () - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-comint-prompts-goto-other-window))) -(put 'helm-comint-prompts-other-window 'helm-only t) - -(defun helm-comint-prompts-other-frame () - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-comint-prompts-goto-other-frame))) -(put 'helm-comint-prompts-other-frame 'helm-only t) - -;;;###autoload -(defun helm-comint-prompts () - "Pre-configured `helm' to browse the prompts of the current comint buffer." - (interactive) - (if (apply 'derived-mode-p helm-comint-mode-list) - (helm :sources - (helm-build-sync-source "Comint prompts" - :candidates (helm-comint-prompts-list major-mode) - :candidate-transformer 'helm-comint-prompts-transformer - :action '(("Go to prompt" . helm-comint-prompts-goto))) - :buffer "*helm comint prompts*") - (message "Current buffer is not a comint buffer"))) - -;;;###autoload -(defun helm-comint-prompts-all () - "Pre-configured `helm' to browse the prompts of all comint sessions." - (interactive) - (if (apply 'derived-mode-p helm-comint-mode-list) - (helm :sources - (helm-build-sync-source "All comint prompts" - :candidates (helm-comint-prompts-list-all major-mode) - :candidate-transformer 'helm-comint-prompts-all-transformer - :action (quote (("Go to prompt" . helm-comint-prompts-goto) - ("Go to prompt in other window `C-c o`" . - helm-comint-prompts-goto-other-window) - ("Go to prompt in other frame `C-c C-o`" . - helm-comint-prompts-goto-other-frame))) - :keymap helm-comint-prompts-keymap) - :buffer "*helm comint all prompts*") - (message "Current buffer is not a comint buffer"))) - -;;; Comint history -;; -;; -(defun helm-comint-input-ring-action (candidate) - "Default action for comint history." - (with-helm-current-buffer - (delete-region (comint-line-beginning-position) (point-max)) - (insert candidate))) - -(defvar helm-source-comint-input-ring - (helm-build-sync-source "Comint history" - :candidates (lambda () - (with-helm-current-buffer - (cl-loop for elm in (ring-elements comint-input-ring) - unless (string= elm "") - collect elm))) - :action 'helm-comint-input-ring-action - ;; Multiline does not work for `shell' because of an Emacs bug. - ;; It works in other REPLs like Geiser. - :multiline 'helm-comint-max-offset) - "Source that provides Helm completion against `comint-input-ring'.") - -;;;###autoload -(defun helm-comint-input-ring () - "Preconfigured `helm' that provide completion of `comint' history." - (interactive) - (when (derived-mode-p 'comint-mode) - (helm :sources 'helm-source-comint-input-ring - :input (buffer-substring-no-properties (comint-line-beginning-position) - (point-at-eol)) - :buffer "*helm comint history*"))) - -(provide 'helm-comint) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-comint.el ends here diff --git a/elpa/helm-20191031.725/helm-command.el b/elpa/helm-20191031.725/helm-command.el deleted file mode 100644 index 54aae483..00000000 --- a/elpa/helm-20191031.725/helm-command.el +++ /dev/null @@ -1,308 +0,0 @@ -;;; helm-command.el --- Helm execute-exended-command. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'cl-lib) -(require 'helm) -(require 'helm-help) -(require 'helm-mode) -(require 'helm-elisp) - - -(defgroup helm-command nil - "Emacs command related Applications and libraries for Helm." - :group 'helm) - -(defcustom helm-M-x-requires-pattern 0 - "Value of requires-pattern for `helm-M-x'. -Show all candidates on startup when 0 (default)." - :group 'helm-command - :type 'boolean) - -(defcustom helm-M-x-always-save-history nil - "`helm-M-x' Save command in `extended-command-history' even when it fail." - :group 'helm-command - :type 'boolean) - -(defcustom helm-M-x-reverse-history nil - "The history source of `helm-M-x' appear in second position when non--nil." - :group 'helm-command - :type 'boolean) - -(defcustom helm-M-x-fuzzy-match nil - "Enable fuzzy matching in `helm-M-x' when non--nil." - :group 'helm-command - :type 'boolean) - -(defcustom helm-M-x-default-sort-fn #'helm-M-x-fuzzy-sort-candidates - "Default sort function for `helm-M-x'. - -It should sort against REAL value of candidates. - -It is used only when `helm-M-x-fuzzy-match' is enabled." - :group 'helm-command - :type 'function) - -;;; Faces -;; -;; -(defgroup helm-command-faces nil - "Customize the appearance of helm-command." - :prefix "helm-" - :group 'helm-command - :group 'helm-faces) - -(defface helm-M-x-key '((t (:foreground "orange" :underline t))) - "Face used in helm-M-x to show keybinding." - :group 'helm-command-faces) - - -(defvar helm-M-x-input-history nil) -(defvar helm-M-x-prefix-argument nil - "Prefix argument before calling `helm-M-x'.") - - -(defun helm-M-x-get-major-mode-command-alist (mode-map) - "Return alist of MODE-MAP." - (when mode-map - (cl-loop for key being the key-seqs of mode-map using (key-bindings com) - for str-key = (key-description key) - for ismenu = (string-match "" str-key) - unless ismenu collect (cons str-key com)))) - -(defun helm-get-mode-map-from-mode (mode) - "Guess the mode-map name according to MODE. -Some modes don't use conventional mode-map name -so we need to guess mode-map name. e.g python-mode ==> py-mode-map. -Return nil if no mode-map found." - (cl-loop ;; Start with a conventional mode-map name. - with mode-map = (intern-soft (format "%s-map" mode)) - with mode-string = (symbol-name mode) - with mode-name = (replace-regexp-in-string "-mode" "" mode-string) - while (not mode-map) - for count downfrom (length mode-name) - ;; Return when no result after parsing entire string. - when (eq count 0) return nil - for sub-name = (substring mode-name 0 count) - do (setq mode-map (intern-soft (format "%s-map" (concat sub-name "-mode")))) - finally return mode-map)) - -(defun helm-M-x-current-mode-map-alist () - "Return mode-map alist of current `major-mode'." - (let ((map-sym (helm-get-mode-map-from-mode major-mode))) - (when (and map-sym (boundp map-sym)) - (helm-M-x-get-major-mode-command-alist (symbol-value map-sym))))) - - -(defun helm-M-x-transformer-1 (candidates &optional sort) - "Transformer function to show bindings in emacs commands. -Show global bindings and local bindings according to current `major-mode'. -If SORT is non nil sort list with `helm-generic-sort-fn'. -Note that SORT should not be used when fuzzy matching because -fuzzy matching is running its own sort function with a different algorithm." - (with-helm-current-buffer - (cl-loop with local-map = (helm-M-x-current-mode-map-alist) - for cand in candidates - for local-key = (car (rassq cand local-map)) - for key = (substitute-command-keys (format "\\[%s]" cand)) - unless (get (intern (if (consp cand) (car cand) cand)) 'helm-only) - collect - (cons (cond ((and (string-match "^M-x" key) local-key) - (format "%s (%s)" - cand (propertize - local-key - 'face 'helm-M-x-key))) - ((string-match "^M-x" key) cand) - (t (format "%s (%s)" - cand (propertize - key - 'face 'helm-M-x-key)))) - cand) - into ls - finally return - (if sort (sort ls #'helm-generic-sort-fn) ls)))) - -(defun helm-M-x-transformer (candidates _source) - "Transformer function for `helm-M-x' candidates." - (helm-M-x-transformer-1 candidates (null helm--in-fuzzy))) - -(defun helm-M-x-transformer-hist (candidates _source) - "Transformer function for `helm-M-x' candidates." - (helm-M-x-transformer-1 candidates)) - -(defun helm-M-x--notify-prefix-arg () - ;; Notify a prefix-arg set AFTER calling M-x. - (when prefix-arg - (with-helm-window - (helm-display-mode-line (helm-get-current-source) 'force)))) - -(defun helm-cmd--get-current-function-name () - (save-excursion - (beginning-of-defun) - (cadr (split-string (buffer-substring-no-properties - (point-at-bol) (point-at-eol)))))) - -(defun helm-cmd--get-preconfigured-commands (&optional dir) - (let* ((helm-dir (or dir (helm-basedir (locate-library "helm")))) - (helm-autoload-file (expand-file-name "helm-autoloads.el" helm-dir)) - results) - (when (file-exists-p helm-autoload-file) - (with-temp-buffer - (insert-file-contents helm-autoload-file) - (while (re-search-forward "Preconfigured" nil t) - (push (substring (helm-cmd--get-current-function-name) 1) results)))) - results)) - -(defvar helm-M-x-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-comp-read-map) - (define-key map (kbd "C-u") nil) - (define-key map (kbd "C-u") 'helm-M-x-universal-argument) - map)) - -(defun helm-M-x-universal-argument () - "Same as `universal-argument' but for `helm-M-x'." - (interactive) - (if helm-M-x-prefix-argument - (progn (setq helm-M-x-prefix-argument nil) - (let ((inhibit-read-only t)) - (with-selected-window (minibuffer-window) - (save-excursion - (goto-char (point-min)) - (delete-char (- (minibuffer-prompt-width) (length "M-x ")))))) - (message "Initial prefix arg disabled")) - (setq prefix-arg (list 4)) - (universal-argument--mode))) -(put 'helm-M-x-universal-argument 'helm-only t) - -(defun helm-M-x-fuzzy-sort-candidates (candidates _source) - (helm-fuzzy-matching-default-sort-fn-1 candidates t)) - -(defun helm-M-x-read-extended-command (&optional collection history) - "Read command name to invoke in `helm-M-x'. -Helm completion is not provided when executing or defining -kbd macros. -Optional arg COLLECTION is to allow using another COLLECTION -than the default which is OBARRAY." - (if (or defining-kbd-macro executing-kbd-macro) - (if helm-mode - (unwind-protect - (progn - (helm-mode -1) - (read-extended-command)) - (helm-mode 1)) - (read-extended-command)) - (let* ((helm-fuzzy-sort-fn helm-M-x-default-sort-fn) - (helm--mode-line-display-prefarg t) - (tm (run-at-time 1 0.1 'helm-M-x--notify-prefix-arg)) - (helm-move-selection-after-hook - (cons (lambda () (setq current-prefix-arg nil)) - helm-move-selection-after-hook))) - (setq extended-command-history - (cl-loop for c in extended-command-history - when (and c (commandp (intern c))) - do (set-text-properties 0 (length c) nil c) - and collect c)) - (unwind-protect - (progn - (setq current-prefix-arg nil) - (helm-comp-read - (concat (cond - ((eq helm-M-x-prefix-argument '-) "- ") - ((and (consp helm-M-x-prefix-argument) - (eq (car helm-M-x-prefix-argument) 4)) "C-u ") - ((and (consp helm-M-x-prefix-argument) - (integerp (car helm-M-x-prefix-argument))) - (format "%d " (car helm-M-x-prefix-argument))) - ((integerp helm-M-x-prefix-argument) - (format "%d " helm-M-x-prefix-argument))) - "M-x ") - (or collection obarray) - :test 'commandp - :requires-pattern helm-M-x-requires-pattern - :name "Emacs Commands" - :buffer "*helm M-x*" - :persistent-action (lambda (candidate) - (helm-elisp--persistent-help - candidate 'helm-describe-function)) - :persistent-help "Describe this command" - :history (or history extended-command-history) - :reverse-history helm-M-x-reverse-history - :input-history 'helm-M-x-input-history - :del-input nil - :help-message 'helm-M-x-help-message - :group 'helm-command - :keymap helm-M-x-map - :must-match t - :match-part (lambda (c) (car (split-string c))) - :fuzzy helm-M-x-fuzzy-match - :nomark t - :candidates-in-buffer t - :fc-transformer 'helm-M-x-transformer - :hist-fc-transformer 'helm-M-x-transformer-hist)) - (cancel-timer tm) - (setq helm--mode-line-display-prefarg nil))))) - -;;;###autoload -(defun helm-M-x (_arg &optional command-name) - "Preconfigured `helm' for Emacs commands. -It is `helm' replacement of regular `M-x' `execute-extended-command'. - -Unlike regular `M-x' emacs vanilla `execute-extended-command' command, -the prefix args if needed, can be passed AFTER starting `helm-M-x'. -When a prefix arg is passed BEFORE starting `helm-M-x', the first `C-u' -while in `helm-M-x' session will disable it. - -You can get help on each command by persistent action." - (interactive - (progn - (setq helm-M-x-prefix-argument current-prefix-arg) - (list current-prefix-arg (helm-M-x-read-extended-command)))) - (when (stringp command-name) - (unless (string= command-name "") - (let ((sym-com (and (stringp command-name) (intern-soft command-name)))) - (when sym-com - ;; Avoid having `this-command' set to *exit-minibuffer. - (setq this-command sym-com - ;; Handle C-x z (repeat) Issue #322 - real-this-command sym-com) - ;; If helm-M-x is called with regular emacs completion (kmacro) - ;; use the value of arg otherwise use helm-current-prefix-arg. - (let ((prefix-arg (or helm-current-prefix-arg helm-M-x-prefix-argument))) - (cl-flet ((save-hist (command) - (setq extended-command-history - (cons command (delete command extended-command-history))))) - (condition-case-unless-debug err - (progn - (command-execute sym-com 'record) - (save-hist command-name)) - (error - (when helm-M-x-always-save-history - (save-hist command-name)) - (signal (car err) (cdr err))))))))))) -(put 'helm-M-x 'interactive-only 'command-execute) - -(provide 'helm-command) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-command.el ends here diff --git a/elpa/helm-20191031.725/helm-config.el b/elpa/helm-20191031.725/helm-config.el deleted file mode 100644 index 36107538..00000000 --- a/elpa/helm-20191031.725/helm-config.el +++ /dev/null @@ -1,172 +0,0 @@ -;;; helm-config.el --- Applications library for `helm.el' -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - - -;;; Require -;; -;; -(declare-function async-bytecomp-package-mode "ext:async-bytecomp.el") -(when (require 'async-bytecomp nil t) - (and (fboundp 'async-bytecomp-package-mode) - (async-bytecomp-package-mode 1))) - - -(defgroup helm-config nil - "Various configurations for Helm." - :group 'helm) - -(defcustom helm-command-prefix-key "C-x c" - "The key `helm-command-prefix' is bound to in the global map." - :type '(choice (string :tag "Key") (const :tag "no binding")) - :group 'helm-config - :set - (lambda (var key) - (when (and (boundp var) (symbol-value var)) - (define-key (current-global-map) - (read-kbd-macro (symbol-value var)) nil)) - (when key - (define-key (current-global-map) - (read-kbd-macro key) 'helm-command-prefix)) - (set var key))) - -(defcustom helm-minibuffer-history-key "C-r" - "The key `helm-minibuffer-history' is bound to in minibuffer local maps." - :type '(choice (string :tag "Key") (const :tag "no binding")) - :group 'helm-config - :set - (lambda (var key) - (cl-dolist (map '(minibuffer-local-completion-map - minibuffer-local-filename-completion-map - minibuffer-local-filename-must-match-map ; Emacs 23.1.+ - minibuffer-local-isearch-map - minibuffer-local-map - minibuffer-local-must-match-filename-map ; Older Emacsen - minibuffer-local-must-match-map - minibuffer-local-ns-map)) - (when (and (boundp map) (keymapp (symbol-value map))) - (when (and (boundp var) (symbol-value var)) - (define-key (symbol-value map) - (read-kbd-macro (symbol-value var)) nil)) - (when key - (define-key (symbol-value map) - (read-kbd-macro key) 'helm-minibuffer-history)))) - (set var key))) - -;;; Command Keymap -;; -;; -(defvar helm-command-map - (let ((map (make-sparse-keymap))) - (define-key map (kbd "a") 'helm-apropos) - (define-key map (kbd "e") 'helm-etags-select) - (define-key map (kbd "l") 'helm-locate) - (define-key map (kbd "s") 'helm-surfraw) - (define-key map (kbd "r") 'helm-regexp) - (define-key map (kbd "m") 'helm-man-woman) - (define-key map (kbd "t") 'helm-top) - (define-key map (kbd "/") 'helm-find) - (define-key map (kbd "i") 'helm-semantic-or-imenu) - (define-key map (kbd "I") 'helm-imenu-in-all-buffers) - (define-key map (kbd "") 'helm-lisp-completion-at-point) - (define-key map (kbd "p") 'helm-list-emacs-process) - (define-key map (kbd "C-x r b") 'helm-filtered-bookmarks) - (define-key map (kbd "M-y") 'helm-show-kill-ring) - (define-key map (kbd "C-c ") 'helm-all-mark-rings) - (define-key map (kbd "C-x C-f") 'helm-find-files) - (define-key map (kbd "f") 'helm-multi-files) - (define-key map (kbd "C-:") 'helm-eval-expression-with-eldoc) - (define-key map (kbd "C-,") 'helm-calcul-expression) - (define-key map (kbd "M-x") 'helm-M-x) - (define-key map (kbd "M-s o") 'helm-occur) - (define-key map (kbd "M-g a") 'helm-do-grep-ag) - (define-key map (kbd "c") 'helm-colors) - (define-key map (kbd "F") 'helm-select-xfont) - (define-key map (kbd "8") 'helm-ucs) - (define-key map (kbd "C-c f") 'helm-recentf) - (define-key map (kbd "C-c g") 'helm-google-suggest) - (define-key map (kbd "h i") 'helm-info-at-point) - (define-key map (kbd "h r") 'helm-info-emacs) - (define-key map (kbd "h g") 'helm-info-gnus) - (define-key map (kbd "h h") 'helm-documentation) - (define-key map (kbd "C-x C-b") 'helm-buffers-list) - (define-key map (kbd "C-x r i") 'helm-register) - (define-key map (kbd "C-c C-x") 'helm-run-external-command) - (define-key map (kbd "b") 'helm-resume) - (define-key map (kbd "M-g i") 'helm-gid) - (define-key map (kbd "@") 'helm-list-elisp-packages) - map)) - -;; Don't override the keymap we just defined with an empty -;; keymap. This also protect bindings changed by the user. -(defvar helm-command-prefix) -(define-prefix-command 'helm-command-prefix) -(fset 'helm-command-prefix helm-command-map) -(setq helm-command-prefix helm-command-map) - - -;;; Menu - -(require 'helm-easymenu) - - -;;;###autoload -(defun helm-configuration () - "Customize `helm'." - (interactive) - (customize-group "helm")) - - -;;; Fontlock -(cl-dolist (mode '(emacs-lisp-mode lisp-interaction-mode)) - (font-lock-add-keywords - mode - '(("(\\<\\(with-helm-after-update-hook\\)\\>" 1 font-lock-keyword-face) - ("(\\<\\(with-helm-temp-hook\\)\\>" 1 font-lock-keyword-face) - ("(\\<\\(with-helm-window\\)\\>" 1 font-lock-keyword-face) - ("(\\<\\(with-helm-quittable\\)\\>" 1 font-lock-keyword-face) - ("(\\<\\(with-helm-current-buffer\\)\\>" 1 font-lock-keyword-face) - ("(\\<\\(with-helm-buffer\\)\\>" 1 font-lock-keyword-face) - ("(\\<\\(with-helm-show-completion\\)\\>" 1 font-lock-keyword-face) - ("(\\<\\(with-helm-default-directory\\)\\>" 1 font-lock-keyword-face) - ("(\\<\\(with-helm-restore-variables\\)\\>" 1 font-lock-keyword-face) - ("(\\<\\(helm-multi-key-defun\\)\\>" 1 font-lock-keyword-face) - ("(\\<\\(helm-while-no-input\\)\\>" 1 font-lock-keyword-face) - ("(\\<\\(helm-aif\\)\\>" 1 font-lock-keyword-face) - ("(\\<\\(helm-awhile\\)\\>" 1 font-lock-keyword-face) - ("(\\<\\(helm-acond\\)\\>" 1 font-lock-keyword-face) - ("(\\<\\(helm-aand\\)\\>" 1 font-lock-keyword-face) - ("(\\<\\(helm-with-gensyms\\)\\>" 1 font-lock-keyword-face) - ("(\\<\\(helm-read-answer\\)\\>" 1 font-lock-keyword-face)))) - - -;;; Load the autoload file -;; It should have been generated either by -;; package.el or the make file. - -(load "helm-autoloads" nil t) - -(provide 'helm-config) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-config.el ends here diff --git a/elpa/helm-20191031.725/helm-dabbrev.el b/elpa/helm-20191031.725/helm-dabbrev.el deleted file mode 100644 index 6adce190..00000000 --- a/elpa/helm-20191031.725/helm-dabbrev.el +++ /dev/null @@ -1,388 +0,0 @@ -;;; helm-dabbrev.el --- Helm implementation of dabbrev. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'helm) -(require 'helm-lib) -(require 'helm-help) -(require 'helm-elisp) ; For show-completion. - -(defgroup helm-dabbrev nil - "Dabbrev related Applications and libraries for Helm." - :group 'helm) - -(defcustom helm-dabbrev-always-search-all t - "Always search in all buffers when non--nil. -Note that even if nil, a search in all buffers -will occur if the length of candidates is <= than -`helm-dabbrev-max-length-result'." - :group 'helm-dabbrev - :type 'boolean) - -(defcustom helm-dabbrev-candidates-number-limit 1000 - "Maximum number of candidates to collect. - -Higher this number is, slower the computation of candidates will be. -You can use safely a higher value with emacs-26+. -Note that this have nothing to do with `helm-candidate-number-limit'." - :group 'helm-dabbrev - :type 'integer) - -(defcustom helm-dabbrev-ignored-buffers-regexps - '("\\*helm" "\\*Messages" "\\*Echo Area" "\\*Buffer List") - "List of regexps matching names of buffers that helm-dabbrev should not check." - :group 'helm-dabbrev - :type '(repeat regexp)) - -(defcustom helm-dabbrev-related-buffer-fn #'helm-dabbrev--same-major-mode-p - "A function that decide if a buffer to search in is related to `current-buffer'. -This is actually determined by comparing `major-mode' of the buffer to search -and the `current-buffer'. -The function take one arg, the buffer which is current, look at -`helm-dabbrev--same-major-mode-p' for example. - -When nil all buffers are considered related to `current-buffer'." - :group 'helm-dabbrev - :type 'function) - -(defcustom helm-dabbrev-major-mode-assoc nil - "Major mode association alist. -This allow helm-dabbrev searching in buffers with the associated `major-mode'. -e.g \(emacs-lisp-mode . lisp-interaction-mode\) -will allow searching in the lisp-interaction-mode buffer when `current-buffer' -is an `emacs-lisp-mode' buffer and vice versa i.e -no need to provide \(lisp-interaction-mode . emacs-lisp-mode\) association. - -When nil check is the searched buffer have same `major-mode' -than the `current-buffer'. -This have no effect when `helm-dabbrev-related-buffer-fn' is nil or of course -bound to a function that doesn't handle this var." - :type '(alist :key-type symbol :value-type symbol) - :group 'helm-dabbrev) - -(defcustom helm-dabbrev-lineno-around 30 - "Search first in this number of lines before an after point." - :group 'helm-dabbrev - :type 'integer) - -(defcustom helm-dabbrev-cycle-threshold 5 - "Number of time helm-dabbrev cycle before displaying helm completion. -When nil or 0 disable cycling." - :group 'helm-dabbrev - :type '(choice (const :tag "Cycling disabled" nil) integer)) - -(defcustom helm-dabbrev-case-fold-search 'smart - "Set `case-fold-search' in `helm-dabbrev'. -Same as `helm-case-fold-search' but for `helm-dabbrev'. -Note that this is not affecting searching in helm buffer, -but the initial search for all candidates in buffer(s)." - :group 'helm-dabbrev - :type '(choice (const :tag "Ignore case" t) - (const :tag "Respect case" nil) - (other :tag "Smart" 'smart))) - -(defcustom helm-dabbrev-use-thread nil - "[EXPERIMENTAL] Compute candidates asynchronously (partially) when non nil. - -The idea is to compute candidates while cycling the first ones, so -this is available only if `helm-dabbrev-cycle-threshold' is not 0 or -nil, also it is available only on emacs-26+ (needs threads). - -This is reasonably working when you don't have to complete a huge list -of candidates, otherwise you will have a small delay after the first cycle -because thread is released unexpectedly when helm-dabbrev exit after -first insertion. - -IOW keep `helm-dabbrev-candidates-number-limit' to a reasonable -value (I don't!) and give enough prefix before completing e.g. for -completing \"helm-dabbrev\" use \"helm-d\" and not \"he\" if you want -to use this." - :group 'helm-dabbrev - :type 'boolean) - -(defvaralias 'helm-dabbrev--regexp 'helm-dabbrev-separator-regexp) -(make-obsolete-variable 'helm-dabbrev--regexp - 'helm-dabbrev-separator-regexp "2.8.3") -;; Check for beginning of line should happen last (^\n\\|^). -(defvar helm-dabbrev-separator-regexp - "\\s-\\|\t\\|[(\\[\\{\"'`=<$;,@.#+]\\|\\s\\\\|^\n\\|^" - "Regexp matching the start of a dabbrev candidate.") - - -(defvar helm-dabbrev-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "M-/") 'helm-next-line) - (define-key map (kbd "M-:") 'helm-previous-line) - map)) - -;; Internal -(defvar helm-dabbrev--cache nil) -(defvar helm-dabbrev--data nil) -(cl-defstruct helm-dabbrev-info dabbrev limits iterator) -(defvar helm-dabbrev--already-tried nil) -(defvar helm-dabbrev--current-thread nil) - - -(defun helm-dabbrev--buffer-list () - (cl-loop for buf in (buffer-list) - unless (cl-loop for r in helm-dabbrev-ignored-buffers-regexps - thereis (string-match r (buffer-name buf))) - collect buf)) - -(defun helm-dabbrev--same-major-mode-p (start-buffer) - "Decide if current-buffer is related to START-BUFFER." - (helm-same-major-mode-p start-buffer helm-dabbrev-major-mode-assoc)) - -(defun helm-dabbrev--collect (str limit ignore-case all) - (let* ((case-fold-search ignore-case) - (buffer1 (current-buffer)) ; start buffer. - (minibuf (minibufferp buffer1)) - result pos-before pos-after - (search-and-store - (lambda (pattern direction) - (while (and (<= (length result) limit) - (cl-case direction - (1 (search-forward pattern nil t)) - (-1 (search-backward pattern nil t)) - (2 (let ((pos - (save-excursion - (forward-line - helm-dabbrev-lineno-around) - (point)))) - (setq pos-after pos) - (search-forward pattern pos t))) - (-2 (let ((pos - (save-excursion - (forward-line - (- helm-dabbrev-lineno-around)) - (point)))) - (setq pos-before pos) - (search-backward pattern pos t))))) - (let* ((pbeg (match-beginning 0)) - (replace-regexp (concat "\\(" helm-dabbrev-separator-regexp - "\\)\\'")) - (match-word (helm-dabbrev--search - pattern pbeg replace-regexp))) - (when (and match-word (not (member match-word result))) - (push match-word result))))))) - (catch 'break - (dolist (buf (if all (helm-dabbrev--buffer-list) - (list (current-buffer)))) - (with-current-buffer buf - (when (or minibuf ; check against all buffers when in minibuffer. - (if helm-dabbrev-related-buffer-fn - (funcall helm-dabbrev-related-buffer-fn buffer1) - t)) - (save-excursion - ;; Start searching before thing before point. - (goto-char (- (point) (length str))) - ;; Search the last 30 lines before point. - (funcall search-and-store str -2)) ; store pos [1] - (save-excursion - ;; Search the next 30 lines after point. - (funcall search-and-store str 2)) ; store pos [2] - (save-excursion - ;; Search all before point. - ;; If limit is reached in previous call of - ;; search-and-store pos-before is never set and - ;; goto-char will fail, so check it. - (when pos-before - (goto-char pos-before) ; start from [1] - (funcall search-and-store str -1))) - (save-excursion - ;; Search all after point. - ;; Same comment as above for pos-after. - (when pos-after - (goto-char pos-after) ; start from [2] - (funcall search-and-store str 1))))) - (when (>= (length result) limit) (throw 'break nil)))) - (nreverse result))) - -(defun helm-dabbrev--search (pattern beg sep-regexp) - "Search word or symbol at point matching PATTERN. -Argument BEG is corresponding to the previous match-beginning search. -The search starts at (1- BEG) with a regexp starting with -`helm-dabbrev-separator-regexp' followed by PATTERN followed by a -regexp matching syntactically any word or symbol. -The possible false positives matching SEP-REGEXP at end are finally -removed." - (let ((eol (point-at-eol))) - (save-excursion - (goto-char (1- beg)) - (when (re-search-forward - (concat "\\(" - helm-dabbrev-separator-regexp - "\\)" - "\\(?99:\\(" - (regexp-quote pattern) - "\\(\\sw\\|\\s_\\)+\\)\\)") - eol t) - (replace-regexp-in-string - sep-regexp "" - (match-string-no-properties 99)))))) - -(defun helm-dabbrev--get-candidates (dabbrev &optional limit) - (cl-assert dabbrev nil "[No Match]") - (helm-dabbrev--collect - dabbrev (or limit helm-dabbrev-candidates-number-limit) - (cl-case helm-dabbrev-case-fold-search - (smart (helm-set-case-fold-search-1 dabbrev)) - (t helm-dabbrev-case-fold-search)) - helm-dabbrev-always-search-all)) - -(defun helm-dabbrev-default-action (candidate) - (with-helm-current-buffer - (let* ((limits (helm-bounds-of-thing-before-point - helm-dabbrev-separator-regexp)) - (beg (car limits)) - (end (point))) - (run-with-timer - 0.01 nil - 'helm-insert-completion-at-point - beg end candidate)))) - -;;;###autoload -(cl-defun helm-dabbrev () - "Preconfigured helm for dynamic abbreviations." - (interactive) - (let ((dabbrev (helm-thing-before-point - nil helm-dabbrev-separator-regexp)) - (limits (helm-bounds-of-thing-before-point - helm-dabbrev-separator-regexp)) - (enable-recursive-minibuffers t) - (cycling-disabled-p (or (null helm-dabbrev-cycle-threshold) - (zerop helm-dabbrev-cycle-threshold))) - (helm-execute-action-at-once-if-one t) - (helm-quit-if-no-candidate - (lambda () - (message "[Helm-dabbrev: No expansion found]")))) - (cl-assert (and (stringp dabbrev) (not (string= dabbrev ""))) - nil "[Helm-dabbrev: Nothing found before point]") - (when (and - ;; have been called at least once. - (helm-dabbrev-info-p helm-dabbrev--data) - ;; But user have moved with some other command - ;; in the meaning time. - (not (eq last-command 'helm-dabbrev))) - (setq helm-dabbrev--data nil)) - ;; When candidates are requested in helm directly without cycling, - ;; we need them right now before running helm, so no need to use a - ;; thread here. - (when cycling-disabled-p - (setq helm-dabbrev--cache (helm-dabbrev--get-candidates dabbrev))) - (unless (or cycling-disabled-p - (helm-dabbrev-info-p helm-dabbrev--data)) - (setq helm-dabbrev--data - (make-helm-dabbrev-info - :dabbrev dabbrev - :limits limits - :iterator - (helm-iter-list - (cl-loop for i in (helm-dabbrev--get-candidates - dabbrev helm-dabbrev-cycle-threshold) - when (string-match-p - (concat "^" (regexp-quote dabbrev)) i) - collect i)))) - ;; Thread is released as soon as helm-dabbrev exits after first - ;; insertion so this is unusable for now, keep it like this for - ;; now hooping the situation with threads will be improved in - ;; emacs. The idea is to compute whole list of candidates in - ;; background while cycling with the first - ;; helm-dabbrev-cycle-threshold ones. - (when (and (fboundp 'make-thread) helm-dabbrev-use-thread) - (setq helm-dabbrev--current-thread - (make-thread - (lambda () - (setq helm-dabbrev--cache - (helm-dabbrev--get-candidates dabbrev))))))) - (let ((iter (and (helm-dabbrev-info-p helm-dabbrev--data) - (helm-dabbrev-info-iterator helm-dabbrev--data))) - deactivate-mark) - ;; Cycle until iterator is consumed. - (helm-aif (and iter (helm-iter-next iter)) - (progn - (helm-insert-completion-at-point - (car (helm-dabbrev-info-limits helm-dabbrev--data)) - ;; END is the end of the previous inserted string, not - ;; the end (apart for first insertion) of the initial string. - (cdr limits) it) - ;; Move already tried candidates to end of list. - (push it helm-dabbrev--already-tried)) - ;; Iterator is now empty, reset dabbrev to initial value - ;; and start helm completion. - (let* ((old-dabbrev (if (helm-dabbrev-info-p helm-dabbrev--data) - (helm-dabbrev-info-dabbrev helm-dabbrev--data) - dabbrev)) - (only-one (null (cdr (all-completions - old-dabbrev - helm-dabbrev--already-tried))))) - (unless helm-dabbrev-use-thread - (message "Waiting for helm-dabbrev candidates...") - (setq helm-dabbrev--cache - (helm-dabbrev--get-candidates old-dabbrev))) - ;; If the length of candidates is only one when computed - ;; that's mean the unique matched item have already been - ;; inserted by the iterator, so no need to reinsert the old dabbrev, - ;; just let helm exiting with "No expansion found". - (unless (or only-one cycling-disabled-p) - (setq dabbrev old-dabbrev - limits (helm-dabbrev-info-limits helm-dabbrev--data)) - (setq helm-dabbrev--data nil) - (delete-region (car limits) (point)) - (insert dabbrev)) - ;; Cycling is finished, block until helm-dabbrev--cache have - ;; finished to complete. - (when (and (fboundp 'thread-join) - helm-dabbrev-use-thread - (thread-alive-p helm-dabbrev--current-thread)) - (thread-join helm-dabbrev--current-thread)) - (when (and (null cycling-disabled-p) only-one) - (cl-return-from helm-dabbrev - (message "[Helm-dabbrev: No expansion found]"))) - (with-helm-show-completion (car limits) (cdr limits) - (unwind-protect - (helm :sources - (helm-build-in-buffer-source "Dabbrev Expand" - :data - (cl-loop for cand in helm-dabbrev--cache - unless - (member cand helm-dabbrev--already-tried) - collect cand into lst - finally return - (append lst helm-dabbrev--already-tried)) - :persistent-action 'ignore - :persistent-help "DoNothing" - :keymap helm-dabbrev-map - :action 'helm-dabbrev-default-action - :group 'helm-dabbrev) - :buffer "*helm dabbrev*" - :input (concat "^" dabbrev " ") - :resume 'noresume - :allow-nest t) - (setq helm-dabbrev--already-tried nil)))))))) - -(provide 'helm-dabbrev) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-dabbrev.el ends here diff --git a/elpa/helm-20191031.725/helm-easymenu.el b/elpa/helm-20191031.725/helm-easymenu.el deleted file mode 100644 index eb6878ba..00000000 --- a/elpa/helm-20191031.725/helm-easymenu.el +++ /dev/null @@ -1,87 +0,0 @@ -;;; helm-easymenu.el --- Helm easymenu definitions. -*- lexical-binding: t -*- - -;; Copyright (C) 2015 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'easymenu) - -(easy-menu-add-item - nil '("Tools") - '("Helm" - ["Find any Files/Buffers" helm-multi-files t] - ["Helm Everywhere (Toggle)" helm-mode t] - ["Helm resume" helm-resume t] - "----" - ("Files" - ["Find files" helm-find-files t] - ["Recent Files" helm-recentf t] - ["Locate" helm-locate t] - ["Search Files with find" helm-find t] - ["Bookmarks" helm-filtered-bookmarks t]) - ("Buffers" - ["Find buffers" helm-buffers-list t]) - ("Commands" - ["Emacs Commands" helm-M-x t] - ["Externals Commands" helm-run-external-command t]) - ("Help" - ["Helm Apropos" helm-apropos t]) - ("Info" - ["Info at point" helm-info-at-point t] - ["Emacs Manual index" helm-info-emacs t] - ["Gnus Manual index" helm-info-gnus t] - ["Helm documentation" helm-documentation t]) - ("Elpa" - ["Elisp packages" helm-list-elisp-packages t] - ["Elisp packages no fetch" helm-list-elisp-packages-no-fetch t]) - ("Tools" - ["Occur" helm-occur t] - ["Grep current directory with AG" helm-do-grep-ag t] - ["Gid" helm-gid t] - ["Etags" helm-etags-select t] - ["Lisp complete at point" helm-lisp-completion-at-point t] - ["Browse Kill ring" helm-show-kill-ring t] - ["Browse register" helm-register t] - ["Mark Ring" helm-all-mark-rings t] - ["Regexp handler" helm-regexp t] - ["Colors & Faces" helm-colors t] - ["Show xfonts" helm-select-xfont t] - ["Ucs Symbols" helm-ucs t] - ["Imenu" helm-imenu t] - ["Imenu all" helm-imenu-in-all-buffers t] - ["Semantic or Imenu" helm-semantic-or-imenu t] - ["Google Suggest" helm-google-suggest t] - ["Eval expression" helm-eval-expression-with-eldoc t] - ["Calcul expression" helm-calcul-expression t] - ["Man pages" helm-man-woman t] - ["Top externals process" helm-top t] - ["Emacs internals process" helm-list-emacs-process t]) - "----" - ["Preferred Options" helm-configuration t]) - "Spell Checking") - -(easy-menu-add-item nil '("Tools") '("----") "Spell Checking") - - -(provide 'helm-easymenu) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-easymenu.el ends here diff --git a/elpa/helm-20191031.725/helm-elisp-package.el b/elpa/helm-20191031.725/helm-elisp-package.el deleted file mode 100644 index 77f2c763..00000000 --- a/elpa/helm-20191031.725/helm-elisp-package.el +++ /dev/null @@ -1,463 +0,0 @@ -;;; helm-elisp-package.el --- helm interface for package.el -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: -(require 'cl-lib) -(require 'helm) -(require 'helm-help) -(require 'package) - -(defgroup helm-el-package nil - "helm elisp packages." - :group 'helm) - -(defcustom helm-el-package-initial-filter 'all - "Show only installed, upgraded or all packages at startup." - :group 'helm-el-package - :type '(radio :tag "Initial filter for elisp packages" - (const :tag "Show all packages" all) - (const :tag "Show installed packages" installed) - (const :tag "Show not installed packages" uninstalled) - (const :tag "Show upgradable packages" upgrade))) - -(defcustom helm-el-truncate-lines t - "Truncate lines in helm-buffer when non--nil." - :group 'helm-el-package - :type 'boolean) - -;; internals vars -(defvar helm-el-package--show-only 'all) -(defvar helm-el-package--initialized-p nil) -(defvar helm-el-package--tabulated-list nil) -(defvar helm-el-package--upgrades nil) -(defvar helm-el-package--removable-packages nil) - -;; Shutup bytecompiler for emacs-24* -(defvar package-menu-async) ; Only available on emacs-25. -(declare-function async-byte-recompile-directory "ext:async-bytecomp.el") - -(defun helm-el-package--init () - (let (package-menu-async - (inhibit-read-only t)) - (when (null package-alist) - (setq helm-el-package--show-only 'all)) - (when (setq helm-el-package--removable-packages - (package--removable-packages)) - (package-autoremove)) - (unwind-protect - (progn - (save-selected-window - (if helm-el-package--initialized-p - ;; Use this as `list-packages' doesn't work - ;; properly (empty buffer) when called from lisp - ;; with 'no-fetch (emacs-25 WA). - (package-show-package-list) - (when helm--force-updating-p (message "Refreshing packages list...")) - (list-packages helm-el-package--initialized-p)) - (setq helm-el-package--initialized-p t) - (message nil)) - (helm-init-candidates-in-buffer - 'global - (with-current-buffer (get-buffer "*Packages*") - (setq helm-el-package--tabulated-list tabulated-list-entries) - (remove-text-properties (point-min) (point-max) - '(read-only button follow-link category)) - (goto-char (point-min)) - (while (re-search-forward "^[ \t]+" nil t) - (replace-match "")) - (buffer-string))) - (setq helm-el-package--upgrades (helm-el-package-menu--find-upgrades)) - (if helm--force-updating-p - (if helm-el-package--upgrades - (message "Refreshing packages list done, [%d] package(s) to upgrade" - (length helm-el-package--upgrades)) - (message "Refreshing packages list done, no upgrades available")) - (setq helm-el-package--show-only (if helm-el-package--upgrades - 'upgrade - helm-el-package-initial-filter)))) - (kill-buffer "*Packages*")))) - -(defun helm-el-package-describe (candidate) - (let ((id (get-text-property 0 'tabulated-list-id candidate))) - (describe-package (package-desc-name id)))) - -(defun helm-el-package-visit-homepage (candidate) - (let* ((id (get-text-property 0 'tabulated-list-id candidate)) - (pkg (package-desc-name id)) - (desc (cadr (assoc pkg package-archive-contents))) - (extras (package-desc-extras desc)) - (url (and (listp extras) (cdr-safe (assoc :url extras))))) - (if (stringp url) - (browse-url url) - (message "Package %s has no homepage" - (propertize (symbol-name pkg) - 'face 'font-lock-keyword-face))))) - -(defun helm-el-run-visit-homepage () - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-el-package-visit-homepage))) -(put 'helm-el-run-visit-homepage 'helm-only t) - -(defun helm-elisp-package--pkg-name (pkg) - (if (package-desc-p pkg) - (package-desc-name pkg) - pkg)) - -(defun helm-el-package-install-1 (pkg-list) - (cl-loop with mkd = pkg-list - for p in mkd - for id = (get-text-property 0 'tabulated-list-id p) - for name = (helm-elisp-package--pkg-name id) - do (package-install id t) - when (helm-aand (assq name package-alist) - (package-desc-dir (cadr it)) - (file-exists-p it)) - collect id into installed-list and - do (unless (package--user-selected-p name) - (package--save-selected-packages - (cons name package-selected-packages))) - finally do (message (format "%d packages installed:\n(%s)" - (length installed-list) - (mapconcat #'package-desc-full-name - installed-list ", "))))) - -(defun helm-el-package-install (_candidate) - (helm-el-package-install-1 (helm-marked-candidates))) - -(defun helm-el-run-package-install () - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-el-package-install))) -(put 'helm-el-run-package-install 'helm-only t) - -(defun helm-el-package-uninstall-1 (pkg-list &optional force) - (cl-loop with mkd = pkg-list - for p in mkd - for id = (get-text-property 0 'tabulated-list-id p) - do - (condition-case-unless-debug err - (package-delete id force) - (error (message (cadr err)))) - ;; Seems like package-descs are symbols with props instead of - ;; vectors in emacs-27, use package-desc-name to ensure - ;; compatibility in all emacs versions. - unless (assoc (package-desc-name id) package-alist) - collect id into delete-list - finally do (if delete-list - (message (format "%d packages deleted:\n(%s)" - (length delete-list) - (mapconcat #'package-desc-full-name - delete-list ", "))) - "No package deleted"))) - -(defun helm-el-package-uninstall (_candidate) - (helm-el-package-uninstall-1 (helm-marked-candidates) helm-current-prefix-arg)) - -(defun helm-el-run-package-uninstall () - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-el-package-uninstall))) -(put 'helm-el-run-package-uninstall 'helm-only t) - -(defun helm-el-package-menu--find-upgrades () - (cl-loop for entry in helm-el-package--tabulated-list - for pkg-desc = (car entry) - for status = (package-desc-status pkg-desc) - ;; A dependency. - when (string= status "dependency") - collect pkg-desc into dependencies - ;; An installed package used as dependency (user have - ;; installed this package explicitely). - when (package--used-elsewhere-p pkg-desc) - collect pkg-desc into installed-as-dep - ;; An installed package. - when (member status '("installed" "unsigned")) - collect pkg-desc into installed - when (member status '("available" "new")) - collect (cons (package-desc-name pkg-desc) pkg-desc) into available - finally return - ;; Always try to upgrade dependencies before installed. - (cl-loop with all = (append dependencies installed-as-dep installed) - for pkg in all - for name = (package-desc-name pkg) - for avail-pkg = (assq name available) - when (and avail-pkg - (version-list-< - (package-desc-version pkg) - (package-desc-version (cdr avail-pkg)))) - collect avail-pkg))) - -(defun helm-el-package--user-installed-p (package) - "Return non-nil if PACKAGE is a user-installed package." - (let* ((assoc (assq package package-alist)) - (pkg-desc (and assoc (cadr assoc))) - (dir (and pkg-desc (package-desc-dir pkg-desc)))) - (when dir - (file-in-directory-p dir package-user-dir)))) - -(defun helm-el-package-upgrade-1 (pkg-list) - (cl-loop for p in pkg-list - for pkg-desc = (car p) - for pkg-name = (package-desc-name pkg-desc) - for upgrade = (cdr (assq pkg-name - helm-el-package--upgrades)) - do - (cond (;; Install. - (equal pkg-desc upgrade) - (message "Installing package `%s'" pkg-name) - (package-install pkg-desc t)) - (;; Do nothing. - (or (null upgrade) - ;; This may happen when a Elpa version of pkg - ;; is installed and need upgrade and pkg is as - ;; well a builtin package. - (package-built-in-p pkg-name)) - (ignore)) - (;; Delete. - t - (message "Deleting package `%s'" pkg-name) - (package-delete pkg-desc t t))))) - -(defun helm-el-package-upgrade (_candidate) - (helm-el-package-upgrade-1 - (cl-loop with pkgs = (helm-marked-candidates) - for p in helm-el-package--tabulated-list - for pkg = (car p) - if (member (symbol-name (package-desc-name pkg)) pkgs) - collect p))) - -(defun helm-el-run-package-upgrade () - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-el-package-upgrade))) -(put 'helm-el-run-package-upgrade 'helm-only t) - -(defun helm-el-package-upgrade-all () - (if helm-el-package--upgrades - (with-helm-display-marked-candidates - helm-marked-buffer-name (mapcar (lambda (x) (symbol-name (car x))) - helm-el-package--upgrades) - (when (y-or-n-p "Upgrade all packages? ") - (helm-el-package-upgrade-1 helm-el-package--tabulated-list))) - (message "No packages to upgrade actually!"))) - -(defun helm-el-package-upgrade-all-action (_candidate) - (helm-el-package-upgrade-all)) - -(defun helm-el-run-package-upgrade-all () - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-el-package-upgrade-all-action))) -(put 'helm-el-run-package-upgrade-all 'helm-only t) - -(defun helm-el-package--transformer (candidates _source) - (cl-loop for c in candidates - for disp = (concat " " c) - for id = (get-text-property 0 'tabulated-list-id c) - for name = (and id (package-desc-name id)) - for desc = (package-desc-status id) - for built-in-p = (and (package-built-in-p name) - (not (member desc '("available" "new" - "installed" "dependency")))) - for installed-p = (member desc '("installed" "dependency")) - for upgrade-p = (assq name helm-el-package--upgrades) - for user-installed-p = (memq name package-selected-packages) - do (when (and user-installed-p (not upgrade-p)) - (put-text-property 0 2 'display "S " disp)) - do (when (or (memq name helm-el-package--removable-packages) - (and upgrade-p installed-p)) - (put-text-property 0 2 'display "U " disp) - (put-text-property - 2 (+ (length (symbol-name name)) 2) - 'face 'font-lock-variable-name-face disp)) - do (when (and upgrade-p (not installed-p) (not built-in-p)) - (put-text-property 0 2 'display "I " disp)) - for cand = (cons disp (car (split-string disp))) - when (or (and built-in-p - (eq helm-el-package--show-only 'built-in)) - (and upgrade-p - (eq helm-el-package--show-only 'upgrade)) - (and installed-p - (eq helm-el-package--show-only 'installed)) - (and (not installed-p) - (not built-in-p) - (eq helm-el-package--show-only 'uninstalled)) - (eq helm-el-package--show-only 'all)) - collect cand)) - -(defun helm-el-package-show-built-in () - (interactive) - (with-helm-alive-p - (setq helm-el-package--show-only 'built-in) - (helm-update))) -(put 'helm-el-package-show-built-in 'helm-only t) - -(defun helm-el-package-show-upgrade () - (interactive) - (with-helm-alive-p - (setq helm-el-package--show-only 'upgrade) - (helm-update))) -(put 'helm-el-package-show-upgrade 'helm-only t) - -(defun helm-el-package-show-installed () - (interactive) - (with-helm-alive-p - (setq helm-el-package--show-only 'installed) - (helm-update))) -(put 'helm-el-package-show-installed 'helm-only t) - -(defun helm-el-package-show-all () - (interactive) - (with-helm-alive-p - (setq helm-el-package--show-only 'all) - (helm-update))) -(put 'helm-el-package-show-all 'helm-only t) - -(defun helm-el-package-show-uninstalled () - (interactive) - (with-helm-alive-p - (setq helm-el-package--show-only 'uninstalled) - (helm-update))) -(put 'helm-el-package-show-uninstalled 'helm-only t) - -(defvar helm-el-package-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "M-I") 'helm-el-package-show-installed) - (define-key map (kbd "M-O") 'helm-el-package-show-uninstalled) - (define-key map (kbd "M-U") 'helm-el-package-show-upgrade) - (define-key map (kbd "M-B") 'helm-el-package-show-built-in) - (define-key map (kbd "M-A") 'helm-el-package-show-all) - (define-key map (kbd "C-c i") 'helm-el-run-package-install) - (define-key map (kbd "C-c r") 'helm-el-run-package-reinstall) - (define-key map (kbd "C-c d") 'helm-el-run-package-uninstall) - (define-key map (kbd "C-c u") 'helm-el-run-package-upgrade) - (define-key map (kbd "C-c U") 'helm-el-run-package-upgrade-all) - (define-key map (kbd "C-c @") 'helm-el-run-visit-homepage) - map)) - -(defvar helm-source-list-el-package nil) -(defclass helm-list-el-package-source (helm-source-in-buffer) - ((init :initform 'helm-el-package--init) - (get-line :initform 'buffer-substring) - (filtered-candidate-transformer :initform 'helm-el-package--transformer) - (action-transformer :initform 'helm-el-package--action-transformer) - (help-message :initform 'helm-el-package-help-message) - (keymap :initform helm-el-package-map) - (update :initform 'helm-el-package--update) - (candidate-number-limit :initform 9999) - (action :initform '(("Describe package" . helm-el-package-describe) - ("Visit homepage" . helm-el-package-visit-homepage))) - (group :initform 'helm-el-package))) - -(defun helm-el-package--action-transformer (actions candidate) - (let* ((pkg-desc (get-text-property 0 'tabulated-list-id candidate)) - (status (package-desc-status pkg-desc)) - (pkg-name (package-desc-name pkg-desc)) - (built-in (and (package-built-in-p pkg-name) - (not (member status '("available" "new" - "installed" "dependency"))))) - (acts (if helm-el-package--upgrades - (append actions '(("Upgrade all packages" - . helm-el-package-upgrade-all-action))) - actions))) - (cond (built-in '(("Describe package" . helm-el-package-describe))) - ((and (package-installed-p pkg-name) - (cdr (assq pkg-name helm-el-package--upgrades)) - (member status '("installed" "dependency"))) - (append '(("Upgrade package(s)" . helm-el-package-upgrade) - ("Uninstall package(s)" . helm-el-package-uninstall)) - acts)) - ((and (package-installed-p pkg-name) - (cdr (assq pkg-name helm-el-package--upgrades)) - (string= status "available")) - (append '(("Upgrade package(s)" . helm-el-package-upgrade)) - acts)) - ((and (package-installed-p pkg-name) - (or (null (package-built-in-p pkg-name)) - (and (package-built-in-p pkg-name) - (assq pkg-name package-alist)))) - (append acts '(("Reinstall package(s)" . helm-el-package-reinstall) - ("Recompile package(s)" . helm-el-package-recompile) - ("Uninstall package(s)" . helm-el-package-uninstall)))) - (t (append acts '(("Install packages(s)" . helm-el-package-install))))))) - -(defun helm-el-package--update () - (setq helm-el-package--initialized-p nil)) - -(defun helm-el-package-recompile (_pkg) - (cl-loop for p in (helm-marked-candidates) - do (helm-el-package-recompile-1 p))) - -(defun helm-el-package-recompile-1 (pkg) - (let* ((pkg-desc (get-text-property 0 'tabulated-list-id pkg)) - (dir (package-desc-dir pkg-desc))) - (async-byte-recompile-directory dir))) - -(defun helm-el-package-reinstall (_pkg) - (cl-loop for p in (helm-marked-candidates) - for pkg-desc = (get-text-property 0 'tabulated-list-id p) - do (helm-el-package-reinstall-1 pkg-desc))) - -(defun helm-el-package-reinstall-1 (pkg-desc) - (let ((name (package-desc-name pkg-desc))) - (package-delete pkg-desc 'force 'nosave) - ;; pkg-desc contain the description - ;; of the installed package just removed - ;; and is BTW no more valid. - ;; Use the entry in package-archive-content - ;; which is the non--installed package entry. - ;; For some reason `package-install' - ;; need a pkg-desc (package-desc-p) for the build-in - ;; packages already installed, the name (as symbol) - ;; fails with such packages. - (package-install - (cadr (assq name package-archive-contents)) t))) - -(defun helm-el-run-package-reinstall () - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-el-package-reinstall))) -(put 'helm-el-run-package-reinstall 'helm-only t) - -;;;###autoload -(defun helm-list-elisp-packages (arg) - "Preconfigured helm for listing and handling emacs packages." - (interactive "P") - (when arg (setq helm-el-package--initialized-p nil)) - (unless helm-source-list-el-package - (setq helm-source-list-el-package - (helm-make-source "list packages" 'helm-list-el-package-source))) - (helm :sources 'helm-source-list-el-package - :truncate-lines helm-el-truncate-lines - :full-frame t - :buffer "*helm list packages*")) - -;;;###autoload -(defun helm-list-elisp-packages-no-fetch (arg) - "Preconfigured helm for emacs packages. - -Same as `helm-list-elisp-packages' but don't fetch packages on remote. -Called with a prefix ARG always fetch packages on remote." - (interactive "P") - (let ((helm-el-package--initialized-p (null arg))) - (helm-list-elisp-packages nil))) - -(provide 'helm-elisp-package) - -;;; helm-elisp-package.el ends here diff --git a/elpa/helm-20191031.725/helm-elisp.el b/elpa/helm-20191031.725/helm-elisp.el deleted file mode 100644 index 78a5a3ce..00000000 --- a/elpa/helm-20191031.725/helm-elisp.el +++ /dev/null @@ -1,984 +0,0 @@ -;;; helm-elisp.el --- Elisp symbols completion for helm. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: -(require 'cl-lib) -(require 'helm) -(require 'helm-lib) -(require 'helm-help) -(require 'helm-types) -(require 'helm-utils) -(require 'helm-info) -(require 'helm-eval) -(require 'helm-files) - -(declare-function 'helm-describe-function "helm-lib") -(declare-function 'helm-describe-variable "helm-lib") -(declare-function 'helm-describe-face "helm-lib") - - -;;; Customizable values - -(defgroup helm-elisp nil - "Elisp related Applications and libraries for Helm." - :group 'helm) - -(defcustom helm-turn-on-show-completion t - "Display candidate in `current-buffer' while moving selection when non--nil." - :group 'helm-elisp - :type 'boolean) - -(defcustom helm-show-completion-min-window-height 7 - "Minimum completion window height used in show completion. -This is used in macro `with-helm-show-completion'." - :group 'helm-elisp - :type 'integer) - -(defcustom helm-lisp-quoted-function-list - '(funcall apply mapc cl-mapc mapcar cl-mapcar - callf callf2 cl-callf cl-callf2 fset - fboundp fmakunbound symbol-function) - "List of function where quoted function completion happen. -e.g give only function names after \(funcall '." - :group 'helm-elisp - :type '(repeat (choice symbol))) - -(defcustom helm-lisp-unquoted-function-list - '(function defadvice) - "List of function where unquoted function completion happen. -e.g give only function names after \(function ." - :group 'helm-elisp - :type '(repeat (choice symbol))) - -(defcustom helm-apropos-fuzzy-match nil - "Enable fuzzy matching for `helm-apropos' when non-nil." - :group 'helm-elisp - :type 'boolean) - -(defcustom helm-lisp-fuzzy-completion nil - "Enable fuzzy matching in emacs-lisp completion when non-nil. -NOTE: This enable fuzzy matching in helm native implementation of -elisp completion, but not on helmized elisp completion, i.e -fuzzy completion is not available in `completion-at-point'." - :group 'helm-elisp - :type 'boolean) - -(defcustom helm-apropos-function-list '(helm-def-source--emacs-commands - helm-def-source--emacs-functions - helm-def-source--eieio-classes - helm-def-source--eieio-generic - helm-def-source--emacs-variables - helm-def-source--emacs-faces) - "A list of functions that build helm sources to use in `helm-apropos'." - :group 'helm-elisp - :type '(repeat (choice symbol))) - -(defcustom helm-apropos-defaut-info-lookup-sources '(helm-source-info-elisp - helm-source-info-cl - helm-source-info-eieio) - "A list of sources to look into when searching info page of a symbol." - :group 'helm-elisp - :type '(repeat (choice symbol))) - -(defcustom helm-show-completion-display-function - (if (display-graphic-p) - #'helm-display-buffer-in-own-frame - #'helm-show-completion-default-display-function) - "The function used to display helm completion buffer. - -This function is used by `with-helm-show-completion', when nil -fallback to `helm-default-display-buffer'. - -Default is to use a separate frame on graphic display and -`helm-show-completion-default-display-function' on non graphic -display." - :group 'helm-elisp - :type 'function) - -;;; Faces -;; -;; -(defgroup helm-elisp-faces nil - "Customize the appearance of helm-elisp." - :prefix "helm-" - :group 'helm-elisp - :group 'helm-faces) - -(defface helm-lisp-show-completion - '((t (:background "DarkSlateGray"))) - "Face used for showing candidates in `helm-lisp-completion'." - :group 'helm-elisp-faces) - -(defface helm-lisp-completion-info - '((t (:foreground "red"))) - "Face used for showing info in `helm-lisp-completion'." - :group 'helm-elisp-faces) - -(defcustom helm-elisp-help-function - 'helm-elisp-show-help - "Function for displaying help for Lisp symbols." - :group 'helm-elisp - :type '(choice (function :tag "Open help for the symbol." - helm-elisp-show-help) - (function :tag "Show one liner in modeline." - helm-elisp-show-doc-modeline))) - -(defcustom helm-locate-library-fuzzy-match t - "Enable fuzzy-matching in `helm-locate-library' when non--nil." - :type 'boolean - :group 'helm-elisp) - - -;;; Show completion. -;; -;; Provide show completion with macro `with-helm-show-completion'. - -(defvar helm-show-completion-overlay nil) - -;; Called each time cursor move in helm-buffer. -(defun helm-show-completion () - (with-helm-current-buffer - (overlay-put helm-show-completion-overlay - 'display (substring-no-properties - (helm-get-selection))))) - -(defun helm-show-completion-init-overlay (beg end) - (setq helm-show-completion-overlay (make-overlay beg end)) - (overlay-put helm-show-completion-overlay - 'face 'helm-lisp-show-completion)) - -(defun helm-show-completion-default-display-function (buffer &rest _args) - "A special resized helm window is used depending on position in BUFFER." - (with-selected-window (selected-window) - (if (window-dedicated-p) - (helm-default-display-buffer buffer) - (let* ((screen-size (+ (count-screen-lines (window-start) (point) t) - 1 ; mode-line - (if header-line-format 1 0))) ; header-line - (def-size (- (window-height) - helm-show-completion-min-window-height)) - (upper-height (max window-min-height (min screen-size def-size))) - split-window-keep-point) - (recenter -1) - (set-window-buffer (if (active-minibuffer-window) - (minibuffer-selected-window) - (split-window nil upper-height - helm-split-window-default-side)) - buffer))))) - -(defmacro with-helm-show-completion (beg end &rest body) - "Show helm candidate in an overlay at point. -BEG and END are the beginning and end position of the current completion -in `helm-current-buffer'. -BODY is an helm call where we want to enable show completion. -If `helm-turn-on-show-completion' is nil do nothing." - (declare (indent 2) (debug t)) - `(unwind-protect - (if helm-turn-on-show-completion - (let ((helm-move-selection-after-hook - (append (list 'helm-show-completion) - helm-move-selection-after-hook)) - (helm-split-window-default-side - (if (eq helm-split-window-default-side 'same) - 'below helm-split-window-default-side)) - helm-split-window-inside-p - helm-reuse-last-window-split-state) - (helm-set-local-variable - 'helm-display-function - (or helm-show-completion-display-function - 'helm-default-display-buffer)) - (helm-show-completion-init-overlay ,beg ,end) - ,@body) - ,@body) - (when (and helm-show-completion-overlay - (overlayp helm-show-completion-overlay)) - (delete-overlay helm-show-completion-overlay)))) - - -;;; Lisp symbol completion. -;; -;; -(defun helm-lisp-completion--predicate-at-point (beg) - ;; Return a predicate for `all-completions'. - (let ((fn-sym-p (lambda () - (or - (and (eq (char-before) ?\ ) - (save-excursion - (skip-syntax-backward " " (point-at-bol)) - (memq (symbol-at-point) - helm-lisp-unquoted-function-list))) - (and (eq (char-before) ?\') - (save-excursion - (forward-char -1) - (eq (char-before) ?\#))))))) - (save-excursion - (goto-char beg) - (if (or - ;; Complete on all symbols in non--lisp modes (logs mail etc..) - (not (memq major-mode '(emacs-lisp-mode - lisp-interaction-mode - inferior-emacs-lisp-mode))) - (not (or (funcall fn-sym-p) - (and (eq (char-before) ?\') - (save-excursion - (forward-char (if (funcall fn-sym-p) -2 -1)) - (skip-syntax-backward " " (point-at-bol)) - (memq (symbol-at-point) - helm-lisp-quoted-function-list))) - (eq (char-before) ?\())) ; no paren before str. - ;; Looks like we are in a let statement. - (condition-case nil - (progn (up-list -2) (forward-char 1) - (eq (char-after) ?\()) - (error nil))) - (lambda (sym) - (or (boundp sym) (fboundp sym) (symbol-plist sym))) - #'fboundp)))) - -(defun helm-thing-before-point (&optional limits regexp) - "Return symbol name before point. -If REGEXP is specified return what REGEXP find before point. -By default match the beginning of symbol before point. -With LIMITS arg specified return the beginning and end position -of symbol before point." - (save-excursion - (let (beg - (end (point)) - (boundary (field-beginning nil nil (point-at-bol)))) - (if (re-search-backward (or regexp "\\_<") boundary t) - (setq beg (match-end 0)) - (setq beg boundary)) - (unless (= beg end) - (if limits - (cons beg end) - (buffer-substring-no-properties beg end)))))) - -(defun helm-bounds-of-thing-before-point (&optional regexp) - "Get the beginning and end position of `helm-thing-before-point'. -Return a cons \(beg . end\)." - (helm-thing-before-point 'limits regexp)) - -(defun helm-insert-completion-at-point (beg end str) - ;; When there is no space after point - ;; we are completing inside a symbol or - ;; after a partial symbol with the next arg aside - ;; without space, in this case mark the region. - ;; deleting it would remove the - ;; next arg which is unwanted. - (delete-region beg end) - (insert str) - (let ((pos (cdr (or (bounds-of-thing-at-point 'symbol) - ;; needed for helm-dabbrev. - (bounds-of-thing-at-point 'filename))))) - (when (and pos (< (point) pos)) - (push-mark pos t t)))) - -(defvar helm-lisp-completion--cache nil) -(defvar helm-lgst-len nil) -;;;###autoload -(defun helm-lisp-completion-at-point () - "Preconfigured helm for lisp symbol completion at point." - (interactive) - (setq helm-lgst-len 0) - (let* ((target (helm-thing-before-point)) - (beg (car (helm-bounds-of-thing-before-point))) - (end (point)) - (pred (and beg (helm-lisp-completion--predicate-at-point beg))) - (loc-vars (and (fboundp 'elisp--local-variables) - (ignore-errors - (mapcar #'symbol-name (elisp--local-variables))))) - (glob-syms (and target pred (all-completions target obarray pred))) - (candidates (append loc-vars glob-syms)) - (helm-quit-if-no-candidate t) - (helm-execute-action-at-once-if-one t) - (enable-recursive-minibuffers t)) - (setq helm-lisp-completion--cache (cl-loop for sym in candidates - for len = (length sym) - when (> len helm-lgst-len) - do (setq helm-lgst-len len) - collect sym)) - (if candidates - (with-helm-show-completion beg end - ;; Overlay is initialized now in helm-current-buffer. - (helm - :sources (helm-build-in-buffer-source "Lisp completion" - :data helm-lisp-completion--cache - :persistent-action `(helm-lisp-completion-persistent-action . - ,(and (eq helm-elisp-help-function - 'helm-elisp-show-doc-modeline) - 'never-split)) - :nomark t - :match-part (lambda (c) (car (split-string c))) - :fuzzy-match helm-lisp-fuzzy-completion - :persistent-help (helm-lisp-completion-persistent-help) - :filtered-candidate-transformer - 'helm-lisp-completion-transformer - :action (lambda (candidate) - (with-helm-current-buffer - (run-with-timer - 0.01 nil - 'helm-insert-completion-at-point - beg end candidate)))) - :input (if helm-lisp-fuzzy-completion - target (concat target " ")) - :resume 'noresume - :truncate-lines t - :buffer "*helm lisp completion*" - :allow-nest t)) - (message "[No Match]")))) - -(defun helm-lisp-completion-persistent-action (candidate &optional name) - "Show documentation for the function. -Documentation is shown briefly in mode-line or completely -in other window according to the value of `helm-elisp-help-function'." - (funcall helm-elisp-help-function candidate name)) - -(defun helm-lisp-completion-persistent-help () - "Return persistent-help according to the value of `helm-elisp-help-function'" - (cl-ecase helm-elisp-help-function - (helm-elisp-show-doc-modeline "Show brief doc in mode-line") - (helm-elisp-show-help "Toggle show help for the symbol"))) - -(defun helm-elisp--show-help-1 (candidate &optional name) - (let ((sym (intern-soft candidate))) - (cl-typecase sym - ((and fboundp boundp) - (if (member name `(,helm-describe-function-function ,helm-describe-variable-function)) - (funcall (intern (format "helm-%s" name)) sym) - ;; When there is no way to know what to describe - ;; prefer describe-function. - (helm-describe-function sym))) - (fbound (helm-describe-function sym)) - (bound (helm-describe-variable sym)) - (face (helm-describe-face sym))))) - -(defun helm-elisp-show-help (candidate &optional name) - "Show full help for the function CANDIDATE. -Arg NAME specify the name of the top level function -calling helm generic completion (e.g \"describe-function\") -which allow calling the right function when CANDIDATE symbol -refers at the same time to variable and a function." - (helm-elisp--persistent-help - candidate 'helm-elisp--show-help-1 name)) - -(defun helm-elisp-show-doc-modeline (candidate &optional name) - "Show brief documentation for the function in modeline." - (let ((cursor-in-echo-area t) - mode-line-in-non-selected-windows) - (helm-show-info-in-mode-line - (propertize - (helm-get-first-line-documentation - (intern candidate) name) - 'face 'helm-lisp-completion-info)))) - -(defun helm-lisp-completion-transformer (candidates _source) - "Helm candidates transformer for lisp completion." - (cl-loop for c in candidates - for sym = (intern c) - for annot = (cl-typecase sym - (command " (Com)") - (class " (Class)") - (generic " (Gen)") - (fbound " (Fun)") - (bound " (Var)") - (face " (Face)")) - for spaces = (make-string (- helm-lgst-len (length c)) ? ) - collect (cons (concat c spaces annot) c) into lst - finally return (sort lst #'helm-generic-sort-fn))) - -(defun helm-get-first-line-documentation (sym &optional name) - "Return first line documentation of symbol SYM. -If SYM is not documented, return \"Not documented\"." - (let ((doc (cl-typecase sym - ((and fboundp boundp) - (cond ((string= name "describe-function") - (documentation sym t)) - ((string= name "describe-variable") - (documentation-property sym 'variable-documentation t)) - (t (documentation sym t)))) - (fbound (documentation sym t)) - (bound (documentation-property sym 'variable-documentation t)) - (face (face-documentation sym))))) - (if (and doc (not (string= doc "")) - ;; `documentation' return "\n\n(args...)" - ;; for CL-style functions. - (not (string-match-p "^\n\n" doc))) - (car (split-string doc "\n")) - "Not documented"))) - -;;; File completion. -;; -;; Complete file name at point. - -;;;###autoload -(defun helm-complete-file-name-at-point (&optional force) - "Preconfigured helm to complete file name at point." - (interactive) - (require 'helm-mode) - (let* ((tap (thing-at-point 'filename)) - beg - (init (and tap - (or force - (save-excursion - (end-of-line) - (search-backward tap (point-at-bol) t) - (setq beg (point)) - (looking-back "[^'`( ]" (1- (point))))) - (expand-file-name - (substring-no-properties tap)))) - (end (point)) - (helm-quit-if-no-candidate t) - (helm-execute-action-at-once-if-one t) - completion) - (with-helm-show-completion beg end - (setq completion (helm-read-file-name "FileName: " - :initial-input init))) - (when (and completion (not (string= completion ""))) - (delete-region beg end) (insert (if (string-match "^~" tap) - (abbreviate-file-name completion) - completion))))) - -;;;###autoload -(defun helm-lisp-indent () - ;; It is meant to use with `helm-define-multi-key' which - ;; does not support args for functions yet, so use `current-prefix-arg' - ;; for now instead of (interactive "P"). - (interactive) - (let ((tab-always-indent (or (eq tab-always-indent 'complete) - tab-always-indent))) - (indent-for-tab-command current-prefix-arg))) - -;;;###autoload -(defun helm-lisp-completion-or-file-name-at-point () - "Preconfigured helm to complete lisp symbol or filename at point. -Filename completion happen if string start after or between a double quote." - (interactive) - (let* ((tap (thing-at-point 'filename))) - (if (and tap (save-excursion - (end-of-line) - (search-backward tap (point-at-bol) t) - (looking-back "[^'`( ]" (1- (point))))) - (helm-complete-file-name-at-point) - (helm-lisp-completion-at-point)))) - - -;;; Apropos -;; -;; -(defvar helm-apropos-history nil) - -(defun helm-apropos-init (test default) - "Init candidates buffer for `helm-apropos' sources." - (require 'helm-help) - (helm-init-candidates-in-buffer 'global - (let ((default-symbol (and (stringp default) - (intern-soft default))) - (symbols (all-completions "" obarray test))) - (if (and default-symbol (funcall test default-symbol)) - (cons default-symbol symbols) - symbols)))) - -(defun helm-apropos-init-faces (default) - "Init candidates buffer for faces for `helm-apropos'." - (require 'helm-help) - (with-current-buffer (helm-candidate-buffer 'global) - (goto-char (point-min)) - (let ((default-symbol (and (stringp default) - (intern-soft default))) - (faces (face-list))) - (when (and default-symbol (facep default-symbol)) - (insert (concat default "\n"))) - (insert - (mapconcat #'prin1-to-string - (if default - (cl-remove-if (lambda (sym) (string= sym default)) faces) - faces) - "\n"))))) - -(defun helm-apropos-default-sort-fn (candidates _source) - (if (string= helm-pattern "") - candidates - (sort candidates #'helm-generic-sort-fn))) - -(defun helm-apropos-clean-history-variable (candidate) - (with-helm-current-buffer ; var is maybe local - (let* ((sym (intern-soft candidate)) - (cands (symbol-value sym)) - (mkds (and (listp cands) - (helm-comp-read "Delete entry: " - cands :marked-candidates t)))) - (cl-assert (listp mkds) nil "Variable value is not a list") - (cl-loop for elm in mkds do - (if (local-variable-p sym) - (set (make-local-variable sym) - (setq cands (delete elm cands))) - (set sym (setq cands (delete elm cands)))))))) - -(defun helm-apropos-clean-ring (candidate) - (with-helm-current-buffer ; var is maybe local - (let* ((sym (intern-soft candidate)) - (val (symbol-value sym)) - (cands (and (ring-p val) (ring-elements val))) - (mkds (and cands (helm-comp-read - "Delete entry: " - cands :marked-candidates t)))) - (when mkds - (cl-loop for elm in mkds do - (ring-remove - val (helm-position - elm - (ring-elements val) - :test 'equal)) - and do (if (local-variable-p sym) - (set (make-local-variable sym) val) - (set sym val))))))) - -(defun helm-apropos-action-transformer (actions candidate) - (let* ((sym (helm-symbolify candidate)) - (val (with-helm-current-buffer (symbol-value sym)))) - (cond ((custom-variable-p sym) - (append - actions - (let ((standard-value (eval (car (get sym 'standard-value))))) - (unless (equal standard-value (symbol-value sym)) - `(("Reset Variable to default value" - . ,(lambda (candidate) - (let ((sym (helm-symbolify candidate))) - (set sym standard-value))))))) - '(("Customize variable" . - (lambda (candidate) - (customize-option (helm-symbolify candidate))))))) - ((and val (with-helm-current-buffer (ring-p (symbol-value sym)))) - (append actions - '(("Clean ring" . helm-apropos-clean-ring)))) - ((and (string-match-p "history" candidate) (listp val)) - (append actions - '(("Clean variable" . - helm-apropos-clean-history-variable)))) - (t actions)))) - -(defun helm-def-source--emacs-variables (&optional default) - (helm-build-in-buffer-source "Variables" - :init (lambda () - (helm-apropos-init - (lambda (x) (and (boundp x) (not (keywordp x)))) default)) - :fuzzy-match helm-apropos-fuzzy-match - :filtered-candidate-transformer (and (null helm-apropos-fuzzy-match) - 'helm-apropos-default-sort-fn) - :nomark t - :persistent-action (lambda (candidate) - (helm-elisp--persistent-help - candidate 'helm-describe-variable)) - :persistent-help "Toggle describe variable" - :action '(("Describe variable" . helm-describe-variable) - ("Find variable" . helm-find-variable) - ("Info lookup" . helm-info-lookup-symbol) - ("Set variable" . helm-set-variable)) - :action-transformer 'helm-apropos-action-transformer)) - -(defun helm-def-source--emacs-faces (&optional default) - "Create `helm' source for faces to be displayed with -`helm-apropos'." - (helm-build-in-buffer-source "Faces" - :init (lambda () (helm-apropos-init-faces default)) - :fuzzy-match helm-apropos-fuzzy-match - :filtered-candidate-transformer - (append (and (null helm-apropos-fuzzy-match) - '(helm-apropos-default-sort-fn)) - (list - (lambda (candidates _source) - (cl-loop for c in candidates - collect (propertize c 'face (intern c)))))) - :persistent-action (lambda (candidate) - (helm-elisp--persistent-help - candidate 'helm-describe-face)) - :persistent-help "Toggle describe face" - :action '(("Describe face" . helm-describe-face) - ("Find face" . helm-find-face-definition) - ("Customize face" . (lambda (candidate) - (customize-face (helm-symbolify candidate))))))) - -(defun helm-def-source--emacs-commands (&optional default) - (helm-build-in-buffer-source "Commands" - :init (lambda () - (helm-apropos-init 'commandp default)) - :fuzzy-match helm-apropos-fuzzy-match - :filtered-candidate-transformer (and (null helm-apropos-fuzzy-match) - 'helm-apropos-default-sort-fn) - :nomark t - :persistent-action (lambda (candidate) - (helm-elisp--persistent-help - candidate 'helm-describe-function)) - :persistent-help "Toggle describe command" - :action '(("Describe function" . helm-describe-function) - ("Find function" . helm-find-function) - ("Info lookup" . helm-info-lookup-symbol)))) - -(defun helm-def-source--emacs-functions (&optional default) - (helm-build-in-buffer-source "Functions" - :init (lambda () - (helm-apropos-init (lambda (x) - (and (fboundp x) - (not (commandp x)) - (not (generic-p x)) - (not (class-p x)))) - default)) - :fuzzy-match helm-apropos-fuzzy-match - :filtered-candidate-transformer (and (null helm-apropos-fuzzy-match) - 'helm-apropos-default-sort-fn) - :persistent-action (lambda (candidate) - (helm-elisp--persistent-help - candidate 'helm-describe-function)) - :persistent-help "Toggle describe function" - :nomark t - :action '(("Describe function" . helm-describe-function) - ("Find function" . helm-find-function) - ("Info lookup" . helm-info-lookup-symbol)))) - -(defun helm-def-source--eieio-classes (&optional default) - (helm-build-in-buffer-source "Classes" - :init (lambda () - (helm-apropos-init (lambda (x) - (class-p x)) - default)) - :fuzzy-match helm-apropos-fuzzy-match - :filtered-candidate-transformer (and (null helm-apropos-fuzzy-match) - 'helm-apropos-default-sort-fn) - :nomark t - :persistent-action (lambda (candidate) - (helm-elisp--persistent-help - candidate 'helm-describe-class)) - :persistent-help "Toggle describe class" - :action '(("Describe Class" . helm-describe-class) - ("Find Class" . helm-find-function) - ("Info lookup" . helm-info-lookup-symbol)))) - -(defun helm-def-source--eieio-generic (&optional default) - (helm-build-in-buffer-source "Generic functions" - :init (lambda () - (helm-apropos-init (lambda (x) - (generic-p x)) - default)) - :fuzzy-match helm-apropos-fuzzy-match - :filtered-candidate-transformer (and (null helm-apropos-fuzzy-match) - 'helm-apropos-default-sort-fn) - :nomark t - :persistent-action (lambda (candidate) - (helm-elisp--persistent-help - candidate 'helm-describe-function)) - :persistent-help "Toggle describe generic function" - :action '(("Describe function" . helm-describe-function) - ("Find function" . helm-find-function) - ("Info lookup" . helm-info-lookup-symbol)))) - -(defun helm-info-lookup-fallback-source (candidate) - (let ((sym (helm-symbolify candidate)) - src-name fn) - (cond ((class-p sym) - (setq fn #'helm-describe-function - src-name "Describe class")) - ((generic-p sym) - (setq fn #'helm-describe-function - src-name "Describe generic function")) - ((fboundp sym) - (setq fn #'helm-describe-function - src-name "Describe function")) - ((facep sym) - (setq fn #'helm-describe-face - src-name "Describe face")) - (t - (setq fn #'helm-describe-variable - src-name "Describe variable"))) - (helm-build-sync-source src-name - :candidates (list candidate) - :persistent-action (lambda (candidate) - (helm-elisp--persistent-help - candidate fn)) - :persistent-help src-name - :nomark t - :action fn))) - -(defun helm-info-lookup-symbol-1 (c) - (let ((helm-execute-action-at-once-if-one 'current-source)) - (helm :sources (append helm-apropos-defaut-info-lookup-sources - (list (helm-info-lookup-fallback-source c))) - :resume 'noresume - :buffer "*helm lookup*" - :input c))) - -(defun helm-info-lookup-symbol (candidate) - ;; ???:Running an idle-timer allows not catching RET when exiting - ;; with the fallback source. - ;; (run-with-idle-timer 0.01 nil #'helm-info-lookup-symbol-1 candidate) - (helm-info-lookup-symbol-1 candidate)) - -;;;###autoload -(defun helm-apropos (default) - "Preconfigured helm to describe commands, functions, variables and faces. -In non interactives calls DEFAULT argument should be provided as a string, -i.e the `symbol-name' of any existing symbol." - (interactive (list (thing-at-point 'symbol))) - (helm :sources - (mapcar (lambda (func) - (funcall func default)) - helm-apropos-function-list) - :history 'helm-apropos-history - :buffer "*helm apropos*" - :preselect (and default (concat "\\_<" (regexp-quote default) "\\_>")))) - - -;;; Advices -;; -;; -(defvar helm-source-advice - (helm-build-sync-source "Function Advice" - :init (lambda () (require 'advice)) - :candidates 'helm-advice-candidates - :action (helm-make-actions "Toggle Enable/Disable" 'helm-advice-toggle) - :persistent-action 'helm-advice-persistent-action - :nomark t - :multiline t - :persistent-help "Toggle describe function / C-u C-j: Toggle advice")) - -(defun helm-advice-candidates () - (cl-loop for (fname) in ad-advised-functions - for function = (intern fname) - append - (cl-loop for class in ad-advice-classes append - (cl-loop for advice in (ad-get-advice-info-field function class) - for enabled = (ad-advice-enabled advice) - collect - (cons (format - "%s %s %s" - (if enabled "Enabled " "Disabled") - (propertize fname 'face 'font-lock-function-name-face) - (ad-make-single-advice-docstring advice class nil)) - (list function class advice)))))) - -(defun helm-advice-persistent-action (func-class-advice) - (if current-prefix-arg - (helm-advice-toggle func-class-advice) - (describe-function (car func-class-advice)))) - -(defun helm-advice-toggle (func-class-advice) - (cl-destructuring-bind (function _class advice) func-class-advice - (cond ((ad-advice-enabled advice) - (ad-advice-set-enabled advice nil) - (message "Disabled")) - (t - (ad-advice-set-enabled advice t) - (message "Enabled"))) - (ad-activate function) - (and helm-in-persistent-action - (helm-advice-update-current-display-string)))) - -(defun helm-advice-update-current-display-string () - (helm-edit-current-selection - (let ((newword (cond ((looking-at "Disabled") "Enabled") - ((looking-at "Enabled") "Disabled")))) - (when newword - (delete-region (point) (progn (forward-word 1) (point))) - (insert newword))))) - -;;;###autoload -(defun helm-manage-advice () - "Preconfigured `helm' to disable/enable function advices." - (interactive) - (helm-other-buffer 'helm-source-advice "*helm advice*")) - - -;;; Locate elisp library -;; -;; -(defun helm-locate-library-scan-list () - (cl-loop for dir in load-path - with load-suffixes = '(".el") - when (file-directory-p dir) - append (directory-files - dir t (concat (regexp-opt (get-load-suffixes)) - "\\'")))) - -;;;###autoload -(defun helm-locate-library () - "Preconfigured helm to locate elisp libraries." - (interactive) - (helm :sources (helm-build-in-buffer-source "Elisp libraries (Scan)" - :data #'helm-locate-library-scan-list - :fuzzy-match helm-locate-library-fuzzy-match - :keymap helm-generic-files-map - :search (unless helm-locate-library-fuzzy-match - (lambda (regexp) - (re-search-forward - (if helm-ff-transformer-show-only-basename - (replace-regexp-in-string - "\\`\\^" "" regexp) - regexp) - nil t))) - :match-part (lambda (candidate) - (with-helm-buffer - (if helm-ff-transformer-show-only-basename - (helm-basename candidate) candidate))) - :filter-one-by-one (lambda (c) - (with-helm-buffer - (if helm-ff-transformer-show-only-basename - (cons (helm-basename c) c) c))) - :action (helm-actions-from-type-file)) - :ff-transformer-show-only-basename nil - :buffer "*helm locate library*")) - -(defun helm-set-variable (var) - "Set VAR value interactively." - (let* ((sym (helm-symbolify var)) - (val (default-value sym))) - (set-default sym (eval-minibuffer - (format "Set `%s': " var) - (if (or (stringp val) - (memq val '(nil t)) - (numberp val)) - (prin1-to-string val) - (format "'%s" (prin1-to-string val))))))) - - -;;; Elisp Timers. -;; -;; -(defclass helm-absolute-time-timers-class (helm-source-sync helm-type-timers) - ((candidates :initform timer-list) - (allow-dups :initform t) - (candidate-transformer - :initform - (lambda (candidates) - (cl-loop for timer in candidates - collect (cons (helm-elisp--format-timer timer) timer)))))) - -(defvar helm-source-absolute-time-timers - (helm-make-source "Absolute Time Timers" 'helm-absolute-time-timers-class)) - -(defclass helm-idle-time-timers-class (helm-source-sync helm-type-timers) - ((candidates :initform timer-idle-list) - (allow-dups :initform t) - (candidate-transformer - :initform - (lambda (candidates) - (cl-loop for timer in candidates - collect (cons (helm-elisp--format-timer timer) timer)))))) - -(defvar helm-source-idle-time-timers - (helm-make-source "Idle Time Timers" 'helm-idle-time-timers-class)) - -(defun helm-elisp--format-timer (timer) - (format "%s repeat=%s %s(%s)" - (let ((time (timer--time timer))) - (if (timer--idle-delay timer) - (format-time-string "idle-for=%5s" time) - (format-time-string "%m/%d %T" time))) - (or (timer--repeat-delay timer) "nil") - (mapconcat 'identity (split-string - (prin1-to-string (timer--function timer)) - "\n") " ") - (mapconcat 'prin1-to-string (timer--args timer) " "))) - -;;;###autoload -(defun helm-timers () - "Preconfigured `helm' for timers." - (interactive) - (helm :sources '(helm-source-absolute-time-timers - helm-source-idle-time-timers) - :buffer "*helm timers*")) - - -;;; Complex command history -;; -;; -(defun helm-btf--usable-p () - "Return t if current version of `backtrace-frame' accept 2 arguments." - (condition-case nil - (progn (backtrace-frame 1 'condition-case) t) - (wrong-number-of-arguments nil))) - -(if (helm-btf--usable-p) ; Check if BTF accept more than one arg. - ;; Emacs 24.4. - (dont-compile - (defvar helm-sexp--last-sexp nil) - ;; This wont work compiled. - (defun helm-sexp-eval-1 () - (interactive) - (unwind-protect - (progn - ;; Trick called-interactively-p into thinking that `cand' is - ;; an interactive call, See `repeat-complex-command'. - (add-hook 'called-interactively-p-functions - #'helm-complex-command-history--called-interactively-skip) - (eval (read helm-sexp--last-sexp))) - (remove-hook 'called-interactively-p-functions - #'helm-complex-command-history--called-interactively-skip))) - - (defun helm-complex-command-history--called-interactively-skip (i _frame1 frame2) - (and (eq 'eval (cadr frame2)) - (eq 'helm-sexp-eval-1 - (cadr (backtrace-frame (+ i 2) #'called-interactively-p))) - 1)) - - (defun helm-sexp-eval (_candidate) - (call-interactively #'helm-sexp-eval-1))) - ;; Emacs 24.3 - (defun helm-sexp-eval (cand) - (let ((sexp (read cand))) - (condition-case err - (if (> (length (remove nil sexp)) 1) - (eval sexp) - (apply 'call-interactively sexp)) - (error (message "Evaluating gave an error: %S" err) - nil))))) - -(defvar helm-source-complex-command-history - (helm-build-sync-source "Complex Command History" - :candidates (lambda () - ;; Use cdr to avoid adding - ;; `helm-complex-command-history' here. - (cl-loop for i in command-history - unless (equal i '(helm-complex-command-history)) - collect (prin1-to-string i))) - :action (helm-make-actions - "Eval" (lambda (candidate) - (and (boundp 'helm-sexp--last-sexp) - (setq helm-sexp--last-sexp candidate)) - (let ((command (read candidate))) - (unless (equal command (car command-history)) - (setq command-history (cons command command-history)))) - (run-with-timer 0.1 nil #'helm-sexp-eval candidate)) - "Edit and eval" (lambda (candidate) - (edit-and-eval-command "Eval: " (read candidate)))) - :persistent-action #'helm-sexp-eval - :multiline t)) - -;;;###autoload -(defun helm-complex-command-history () - "Preconfigured helm for complex command history." - (interactive) - (helm :sources 'helm-source-complex-command-history - :buffer "*helm complex commands*")) - -(provide 'helm-elisp) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-elisp.el ends here diff --git a/elpa/helm-20191031.725/helm-eshell.el b/elpa/helm-20191031.725/helm-eshell.el deleted file mode 100644 index ac7c9003..00000000 --- a/elpa/helm-20191031.725/helm-eshell.el +++ /dev/null @@ -1,488 +0,0 @@ -;;; helm-eshell.el --- pcomplete and eshell completion for helm. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Commentary: -;; -;; Enable like this in .emacs: -;; (add-hook 'eshell-mode-hook -;; (lambda () -;; (eshell-cmpl-initialize) -;; (define-key eshell-mode-map [remap eshell-pcomplete] 'helm-esh-pcomplete) -;; (define-key eshell-mode-map (kbd "M-s f") 'helm-eshell-prompts-all))) -;; (define-key eshell-mode-map (kbd "M-r") 'helm-eshell-history))) - - -;;; Code: -(require 'cl-lib) -(require 'helm) -(require 'helm-lib) -(require 'helm-help) -(require 'helm-elisp) - -(declare-function eshell-read-aliases-list "em-alias") -(declare-function eshell-send-input "esh-mode" (&optional use-region queue-p no-newline)) -(declare-function eshell-bol "esh-mode") -(declare-function eshell-parse-arguments "esh-arg" (beg end)) -(declare-function eshell-backward-argument "esh-mode" (&optional arg)) -(declare-function helm-quote-whitespace "helm-lib") -(declare-function eshell-skip-prompt "em-prompt") -(defvar eshell-special-chars-outside-quoting) - - -(defgroup helm-eshell nil - "Helm eshell completion and history." - :group 'helm) - - -(defcustom helm-eshell-fuzzy-match nil - "Enable fuzzy matching in `helm-esh-pcomplete' when non--nil." - :group 'helm-eshell - :type 'boolean) - - -(defvar helm-eshell-history-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "M-p") 'helm-next-line) - map) - "Keymap for `helm-eshell-history'.") - -(defvar helm-esh-completion-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "TAB") 'helm-next-line) - map) - "Keymap for `helm-esh-pcomplete'.") - -(defvar helm-eshell--quit-flag nil) - - -(defclass helm-esh-source (helm-source-sync) - ((init :initform (lambda () - (setq pcomplete-current-completions nil - pcomplete-last-completion-raw nil) - ;; Eshell-command add this hook in all minibuffers - ;; Remove it for the helm one. (Fixed in Emacs24) - (remove-hook 'minibuffer-setup-hook 'eshell-mode))) - (candidates :initform 'helm-esh-get-candidates) - ;(nomark :initform t) - (persistent-action :initform 'ignore) - (nohighlight :initform t) - (filtered-candidate-transformer - :initform - (lambda (candidates _sources) - (cl-loop - for i in candidates - collect - (cond ((string-match "\\`~/?" helm-ec-target) - (abbreviate-file-name i)) - ((string-match "\\`/" helm-ec-target) i) - (t - (file-relative-name i))) - into lst - finally return (sort lst 'helm-generic-sort-fn)))) - (action :initform 'helm-ec-insert)) - "Helm class to define source for Eshell completion.") - -;; Internal. -(defvar helm-ec-target "") -(defun helm-ec-insert (_candidate) - "Replace text at point with CANDIDATE. -The function that call this should set `helm-ec-target' to thing at point." - (set (make-local-variable 'comint-file-name-quote-list) - eshell-special-chars-outside-quoting) - (let ((pt (point))) - (when (and helm-ec-target - (search-backward helm-ec-target nil t) - (string= (buffer-substring (point) pt) helm-ec-target)) - (delete-region (point) pt))) - (when (string-match "\\`\\*" helm-ec-target) (insert "*")) - (let ((marked (helm-marked-candidates))) - (prog1 t ;; Makes helm returns t on action. - (insert - (mapconcat - (lambda (x) - (cond ((string-match "\\`~/" helm-ec-target) - ;; Strip out the first escape char added by - ;; `comint-quote-filename' before "~" (Issue #1803). - (substring (comint-quote-filename (abbreviate-file-name x)) 1)) - ((string-match "\\`/" helm-ec-target) - (comint-quote-filename x)) - (t - (concat (and (string-match "\\`[.]/" helm-ec-target) "./") - (comint-quote-filename - (file-relative-name x)))))) - marked " ") - (or (helm-aand (car (last marked)) - (string-match-p "/\\'" it) - "") - " "))))) - -(defun helm-esh-get-candidates () - "Get candidates for eshell completion using `pcomplete'." - (catch 'pcompleted - (with-helm-current-buffer - (let* ((pcomplete-stub) - pcomplete-seen pcomplete-norm-func - pcomplete-args pcomplete-last pcomplete-index - (pcomplete-autolist pcomplete-autolist) - (pcomplete-suffix-list pcomplete-suffix-list) - (table (pcomplete-completions)) - (entry (or (try-completion helm-pattern - (pcomplete-entries)) - helm-pattern))) - (cl-loop ;; expand entry too to be able to compare it with file-cand. - with exp-entry = (and (stringp entry) - (not (string= entry "")) - (file-name-as-directory - (expand-file-name entry default-directory))) - with comps = (all-completions pcomplete-stub table) - unless comps return (prog1 nil - ;; Don't add final space when - ;; there is no completion (issue #1990). - (setq helm-eshell--quit-flag t) - (message "No completions of %s" pcomplete-stub)) - for i in comps - ;; Transform the related names to abs names. - for file-cand = (and exp-entry - (if (file-remote-p i) i - (expand-file-name - i (file-name-directory entry)))) - ;; Compare them to avoid dups. - for file-entry-p = (and (stringp exp-entry) - (stringp file-cand) - ;; Fix :/tmp/foo/ $ cd foo - (not (file-directory-p file-cand)) - (file-equal-p exp-entry file-cand)) - if (and file-cand (or (file-remote-p file-cand) - (file-exists-p file-cand)) - (not file-entry-p)) - collect file-cand into ls - else - ;; Avoid adding entry here. - unless file-entry-p collect i into ls - finally return - (if (and exp-entry - (file-directory-p exp-entry) - ;; If the car of completion list is - ;; an executable, probably we are in - ;; command completion, so don't add a - ;; possible file related entry here. - (and ls (not (executable-find (car ls)))) - ;; Don't add entry if already in prompt. - (not (file-equal-p exp-entry pcomplete-stub))) - (append (list exp-entry) - ;; Entry should not be here now but double check. - (remove entry ls)) - ls)))))) - -;;; Eshell history. -;; -;; -(defclass helm-eshell-history-source (helm-source-sync) - ((init :initform - (lambda () - ;; Same comment as in `helm-source-esh'. - (remove-hook 'minibuffer-setup-hook 'eshell-mode))) - (candidates - :initform - (lambda () - (with-helm-current-buffer - (cl-loop for c from 0 to (ring-length eshell-history-ring) - collect (eshell-get-history c))))) - (nomark :initform t) - (multiline :initform t) - (keymap :initform helm-eshell-history-map) - (candidate-number-limit :initform 9999) - (action :initform (lambda (candidate) - (eshell-kill-input) - (insert candidate)))) - "Helm class to define source for Eshell history.") - - -;;;###autoload -(defun helm-esh-pcomplete () - "Preconfigured helm to provide helm completion in eshell." - (interactive) - (let* ((helm-quit-if-no-candidate t) - (helm-execute-action-at-once-if-one t) - (end (point-marker)) - (beg (save-excursion (eshell-bol) (point))) - (args (catch 'eshell-incomplete - (eshell-parse-arguments beg end))) - (target - (or (and (looking-back " " (1- (point))) " ") - (buffer-substring-no-properties - (save-excursion - (eshell-backward-argument 1) (point)) - end))) - (users-comp (string= target "~")) - (first (car args)) ; Maybe lisp delimiter "(". - last ; Will be the last but parsed by pcomplete. - del-space - del-dot) - (setq helm-ec-target (or target " ") - end (point) - ;; Reset beg for `with-helm-show-completion'. - beg (or (and target (not (string= target " ")) - (- end (length target))) - ;; Nothing at point. - (progn (insert " ") (setq del-space t) (point)))) - (when (string-match "\\`[~.]*.*/[.]\\'" target) - ;; Fix completion on - ;; "~/.", "~/[...]/.", and "../." - (delete-char -1) (setq del-dot t) - (setq helm-ec-target (substring helm-ec-target 0 (1- (length helm-ec-target))))) - (cond ((eq first ?\() - (helm-lisp-completion-or-file-name-at-point)) - ;; In eshell `pcomplete-parse-arguments' is called - ;; with `pcomplete-parse-arguments-function' - ;; locally bound to `eshell-complete-parse-arguments' - ;; which is calling `lisp-complete-symbol', - ;; calling it before would popup the - ;; *completions* buffer. - (t (setq last (replace-regexp-in-string - "\\`\\*" "" - (car (last (ignore-errors - (pcomplete-parse-arguments)))))) - ;; Set helm-eshell--quit-flag to non-nil only on - ;; quit, this tells to not add final suffix when quitting - ;; helm. - (add-hook 'helm-quit-hook 'helm-eshell--quit-hook-fn) - (with-helm-show-completion beg end - (unwind-protect - (or (helm :sources (helm-make-source "Eshell completions" 'helm-esh-source - :fuzzy-match helm-eshell-fuzzy-match) - :buffer "*helm pcomplete*" - :keymap helm-esh-completion-map - :resume 'noresume - :input (if (and (stringp last) - (not (string= last "")) - (not users-comp) - ;; Fix completion on - ;; "../" see #1832. - (or (file-exists-p last) - (helm-aand - (file-name-directory last) - (file-directory-p it)))) - (if (and (file-directory-p last) - (string-match "\\`[~.]*.*/[.]\\'" target)) - ;; Fix completion on - ;; "~/.", "~/[...]/.", and "../." - (expand-file-name - (concat (helm-basedir (file-name-as-directory last)) - (regexp-quote (helm-basename target)))) - (expand-file-name last)) - ;; Don't add "~" to input to - ;; provide completion on all - ;; users instead of only on - ;; current $HOME (#1832). - (unless users-comp last))) - ;; Delete removed dot on quit - (and del-dot (prog1 t (insert "."))) - ;; A space is needed to have completion, remove - ;; it when nothing found. - (and del-space (looking-back "\\s-" (1- (point))) - (delete-char -1)) - (if (and (null helm-eshell--quit-flag) - (and (stringp last) (file-directory-p last)) - (looking-back "\\([.]\\{1,2\\}\\|[^/]\\)\\'" - (1- (point)))) - (prog1 t (insert "/")) - ;; We need another flag for space here, but - ;; global to pass it to `helm-quit-hook', this - ;; space is added when point is just after - ;; previous completion and there is no - ;; more completion, see issue #1832. - (unless (or helm-eshell--quit-flag - (looking-back "/\\'" (1- (point)))) - (prog1 t (insert " "))) - (when (and helm-eshell--quit-flag - (string-match-p "[.]\\{2\\}\\'" last)) - (insert "/")))) - (remove-hook 'helm-quit-hook 'helm-eshell--quit-hook-fn) - (setq helm-eshell--quit-flag nil))))))) - -(defun helm-eshell--quit-hook-fn () - (setq helm-eshell--quit-flag t)) - -;;;###autoload -(defun helm-eshell-history () - "Preconfigured helm for eshell history." - (interactive) - (let* ((end (point)) - (beg (save-excursion (eshell-bol) (point))) - (input (buffer-substring beg end)) - flag-empty) - (when (eq beg end) - (insert " ") - (setq flag-empty t) - (setq end (point))) - (unwind-protect - (with-helm-show-completion beg end - (helm :sources (helm-make-source "Eshell history" - 'helm-eshell-history-source - :fuzzy-match helm-eshell-fuzzy-match) - :buffer "*helm eshell history*" - :resume 'noresume - :input input)) - (when (and flag-empty - (looking-back " " (1- (point)))) - (delete-char -1))))) - - -;;; Eshell prompts -;; -(defface helm-eshell-prompts-promptidx - '((t (:foreground "cyan"))) - "Face used to highlight Eshell prompt index." - :group 'helm-eshell-faces) - -(defface helm-eshell-prompts-buffer-name - '((t (:foreground "green"))) - "Face used to highlight Eshell buffer name." - :group 'helm-eshell-faces) - -(defcustom helm-eshell-prompts-promptidx-p t - "Show prompt number." - :group 'helm-eshell - :type 'boolean) - -(defvar helm-eshell-prompts-keymap - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "C-c o") 'helm-eshell-prompts-other-window) - (define-key map (kbd "C-c C-o") 'helm-eshell-prompts-other-frame) - map) - "Keymap for `helm-eshell-prompt-all'.") - -(defvar eshell-prompt-regexp) -(defvar eshell-highlight-prompt) - -(defun helm-eshell-prompts-list (&optional buffer) - "List the prompts in Eshell BUFFER. - -Return a list of (\"prompt\" (point) (buffer-name) prompt-index)) -e.g. (\"ls\" 162 \"*eshell*\" 3). -If BUFFER is nil, use current buffer." - (with-current-buffer (or buffer (current-buffer)) - (when (eq major-mode 'eshell-mode) - (save-excursion - (goto-char (point-min)) - (let (result (count 1)) - (helm-awhile (re-search-forward eshell-prompt-regexp nil t) - (when (or (and eshell-highlight-prompt - (get-text-property (match-beginning 0) 'read-only)) - (null eshell-highlight-prompt)) - (push (list (buffer-substring-no-properties - it (point-at-eol)) - it (buffer-name) count) - result) - (setq count (1+ count)))) - (nreverse result)))))) - -(defun helm-eshell-prompts-list-all () - "List the prompts of all Eshell buffers. -See `helm-eshell-prompts-list'." - (cl-loop for b in (buffer-list) - append (helm-eshell-prompts-list b))) - -(defun helm-eshell-prompts-transformer (candidates &optional all) - ;; ("ls" 162 "*eshell*" 3) => ("*eshell*:3:ls" . ("ls" 162 "*eshell*" 3)) - (cl-loop for (prt pos buf id) in candidates - collect `(,(concat - (when all - (concat (propertize - buf - 'face 'helm-eshell-prompts-buffer-name) - ":")) - (when helm-eshell-prompts-promptidx-p - (concat (propertize - (number-to-string id) - 'face 'helm-eshell-prompts-promptidx) - ":")) - prt) - . ,(list prt pos buf id)))) - -(defun helm-eshell-prompts-all-transformer (candidates) - (helm-eshell-prompts-transformer candidates t)) - -(cl-defun helm-eshell-prompts-goto (candidate &optional (action 'switch-to-buffer)) - ;; Candidate format: ("ls" 162 "*eshell*" 3) - (let ((buf (nth 2 candidate))) - (unless (and (string= (buffer-name) buf) - (eq action 'switch-to-buffer)) - (funcall action buf)) - (goto-char (nth 1 candidate)) - (recenter))) - -(defun helm-eshell-prompts-goto-other-window (candidate) - (helm-eshell-prompts-goto candidate 'switch-to-buffer-other-window)) - -(defun helm-eshell-prompts-goto-other-frame (candidate) - (helm-eshell-prompts-goto candidate 'switch-to-buffer-other-frame)) - -(defun helm-eshell-prompts-other-window () - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-eshell-prompts-goto-other-window))) -(put 'helm-eshell-prompts-other-window 'helm-only t) - -(defun helm-eshell-prompts-other-frame () - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-eshell-prompts-goto-other-frame))) -(put 'helm-eshell-prompts-other-frame 'helm-only t) - -;;;###autoload -(defun helm-eshell-prompts () - "Pre-configured `helm' to browse the prompts of the current Eshell." - (interactive) - (if (eq major-mode 'eshell-mode) - (helm :sources - (helm-build-sync-source "Eshell prompts" - :candidates (helm-eshell-prompts-list) - :candidate-transformer 'helm-eshell-prompts-transformer - :action '(("Go to prompt" . helm-eshell-prompts-goto))) - :buffer "*helm Eshell prompts*") - (message "Current buffer is not an Eshell buffer"))) - -;;;###autoload -(defun helm-eshell-prompts-all () - "Pre-configured `helm' to browse the prompts of all Eshell sessions." - (interactive) - (helm :sources - (helm-build-sync-source "All Eshell prompts" - :candidates (helm-eshell-prompts-list-all) - :candidate-transformer 'helm-eshell-prompts-all-transformer - :action '(("Go to prompt" . helm-eshell-prompts-goto) - ("Go to prompt in other window `C-c o`" . - helm-eshell-prompts-goto-other-window) - ("Go to prompt in other frame `C-c C-o`" . - helm-eshell-prompts-goto-other-frame)) - :keymap helm-eshell-prompts-keymap) - :buffer "*helm Eshell all prompts*")) - -(provide 'helm-eshell) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-eshell ends here diff --git a/elpa/helm-20191031.725/helm-eval.el b/elpa/helm-20191031.725/helm-eval.el deleted file mode 100644 index caa31020..00000000 --- a/elpa/helm-20191031.725/helm-eval.el +++ /dev/null @@ -1,204 +0,0 @@ -;;; helm-eval.el --- eval expressions from helm. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: -(require 'cl-lib) -(require 'helm) -(require 'helm-help) -(require 'eldoc) -(require 'edebug) - - -(defgroup helm-eval nil - "Eval related Applications and libraries for Helm." - :group 'helm) - -(defcustom helm-eldoc-in-minibuffer-show-fn - 'helm-show-info-in-mode-line - "A function to display eldoc info. -Should take one arg: the string to display." - :group 'helm-eval - :type 'symbol) - -(defcustom helm-show-info-in-mode-line-delay 12 - "Eldoc will show info in mode-line during this delay if user is idle." - :type 'integer - :group 'helm-eval) - - -;;; Eldoc compatibility between emacs-24 and emacs-25 -;; -(if (require 'elisp-mode nil t) ; emacs-25 - ;; Maybe the eldoc functions have been - ;; already aliased by eldoc-eval. - (cl-loop for (f . a) in '((eldoc-current-symbol . - elisp--current-symbol) - (eldoc-fnsym-in-current-sexp . - elisp--fnsym-in-current-sexp) - (eldoc-get-fnsym-args-string . - elisp-get-fnsym-args-string) - (eldoc-get-var-docstring . - elisp-get-var-docstring)) - unless (fboundp f) - do (defalias f a)) - ;; Emacs-24. - (declare-function eldoc-current-symbol "eldoc") - (declare-function eldoc-get-fnsym-args-string "eldoc" (sym &optional index)) - (declare-function eldoc-get-var-docstring "eldoc" (sym)) - (declare-function eldoc-fnsym-in-current-sexp "eldoc")) - -;;; Evaluation Result -;; -;; -;; Internal -(defvar helm-eldoc-active-minibuffers-list nil) - -(defvar helm-eval-expression-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "") 'helm-eval-new-line-and-indent) - (define-key map (kbd "") 'lisp-indent-line) - (define-key map (kbd "") 'helm-lisp-completion-at-point) - (define-key map (kbd "C-p") 'previous-line) - (define-key map (kbd "C-n") 'next-line) - (define-key map (kbd "") 'previous-line) - (define-key map (kbd "") 'next-line) - (define-key map (kbd "") 'forward-char) - (define-key map (kbd "") 'backward-char) - map)) - -(defun helm-build-evaluation-result-source () - (helm-build-dummy-source "Evaluation Result" - :multiline t - :mode-line "C-RET: nl-and-indent, M-tab: reindent, C-tab:complete, C-p/n: next/prec-line." - :filtered-candidate-transformer (lambda (_candidates _source) - (list - (condition-case nil - (with-helm-current-buffer - (pp-to-string - (if edebug-active - (edebug-eval-expression - (read helm-pattern)) - (eval (read helm-pattern))))) - (error "Error")))) - :nohighlight t - :keymap helm-eval-expression-map - :action '(("Copy result to kill-ring" . (lambda (candidate) - (kill-new - (replace-regexp-in-string - "\n" "" candidate)) - (message "Result copied to kill-ring"))) - ("copy sexp to kill-ring" . (lambda (_candidate) - (kill-new helm-input) - (message "Sexp copied to kill-ring")))))) - -(defun helm-eval-new-line-and-indent () - (interactive) - (newline) (lisp-indent-line)) - -(defun helm-eldoc-store-minibuffer () - "Store minibuffer buffer name in `helm-eldoc-active-minibuffers-list'." - (with-selected-window (minibuffer-window) - (push (current-buffer) helm-eldoc-active-minibuffers-list))) - -(defun helm-eldoc-show-in-eval () - "Return eldoc in mode-line for current minibuffer input." - (let ((buf (window-buffer (active-minibuffer-window)))) - (condition-case err - (when (member buf helm-eldoc-active-minibuffers-list) - (with-current-buffer buf - (let* ((sym (save-excursion - (unless (looking-back ")\\|\"" (1- (point))) - (forward-char -1)) - (eldoc-current-symbol))) - (info-fn (eldoc-fnsym-in-current-sexp)) - (doc (or (eldoc-get-var-docstring sym) - (eldoc-get-fnsym-args-string - (car info-fn) (cadr info-fn))))) - (when doc (funcall helm-eldoc-in-minibuffer-show-fn doc))))) - (error (message "Eldoc in minibuffer error: %S" err) nil)))) - -(defun helm-show-info-in-mode-line (str) - "Display string STR in mode-line." - (save-selected-window - (with-current-buffer helm-buffer - (let ((mode-line-format (concat " " str))) - (force-mode-line-update) - (sit-for helm-show-info-in-mode-line-delay)) - (force-mode-line-update)))) - -;;; Calculation Result -;; -;; -(defvar helm-source-calculation-result - (helm-build-dummy-source "Calculation Result" - :filtered-candidate-transformer (lambda (_candidates _source) - (list - (condition-case nil - (calc-eval helm-pattern) - (error "error")))) - :nohighlight t - :action '(("Copy result to kill-ring" . (lambda (candidate) - (kill-new candidate) - (message "Result \"%s\" copied to kill-ring" - candidate))) - ("Copy operation to kill-ring" . (lambda (_candidate) - (kill-new helm-input) - (message "Calculation copied to kill-ring")))))) - -;;;###autoload -(defun helm-eval-expression (arg) - "Preconfigured helm for `helm-source-evaluation-result'." - (interactive "P") - (helm :sources (helm-build-evaluation-result-source) - :input (when arg (thing-at-point 'sexp)) - :buffer "*helm eval*" - :echo-input-in-header-line nil - :history 'read-expression-history)) - -(defvar eldoc-idle-delay) -;;;###autoload -(defun helm-eval-expression-with-eldoc () - "Preconfigured helm for `helm-source-evaluation-result' with `eldoc' support." - (interactive) - (let ((timer (run-with-idle-timer - eldoc-idle-delay 'repeat - 'helm-eldoc-show-in-eval))) - (unwind-protect - (minibuffer-with-setup-hook - 'helm-eldoc-store-minibuffer - (call-interactively 'helm-eval-expression)) - (and timer (cancel-timer timer)) - (setq helm-eldoc-active-minibuffers-list - (cdr helm-eldoc-active-minibuffers-list))))) - -;;;###autoload -(defun helm-calcul-expression () - "Preconfigured helm for `helm-source-calculation-result'." - (interactive) - (helm :sources 'helm-source-calculation-result - :buffer "*helm calcul*")) - -(provide 'helm-eval) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-eval.el ends here diff --git a/elpa/helm-20191031.725/helm-external.el b/elpa/helm-20191031.725/helm-external.el deleted file mode 100644 index e539cde4..00000000 --- a/elpa/helm-20191031.725/helm-external.el +++ /dev/null @@ -1,213 +0,0 @@ -;;; helm-external.el --- Run Externals commands within Emacs with helm completion. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'cl-lib) -(require 'helm) -(require 'helm-help) -(require 'helm-net) - - -(defgroup helm-external nil - "External related Applications and libraries for Helm." - :group 'helm) - -(defcustom helm-raise-command nil - "A shell command to jump to a window running specific program. -Need external program wmctrl. -This will be use with `format', so use something like \"wmctrl -xa %s\"." - :type 'string - :group 'helm-external) - -(defcustom helm-external-programs-associations nil - "Alist to store externals programs associated with file extension. -This variable overhide setting in .mailcap file. -e.g : '\(\(\"jpg\" . \"gqview\"\) (\"pdf\" . \"xpdf\"\)\) " - :type '(alist :key-type string :value-type string) - :group 'helm-external) - -(defcustom helm-default-external-file-browser "nautilus" - "Default external file browser for your system. -Directories will be opened externally with it when -opening file externally in `helm-find-files'. -Set to nil if you do not have external file browser -or do not want to use it. -Windows users should set that to \"explorer.exe\"." - :group 'helm-external - :type 'string) - - -;;; Internals -(defvar helm-external-command-history nil) -(defvar helm-external-commands-list nil - "A list of all external commands the user can execute. -If this variable is not set by the user, it will be calculated -automatically.") - -(defun helm-external-commands-list-1 (&optional sort) - "Returns a list of all external commands the user can execute. -If `helm-external-commands-list' is non-nil it will -return its contents. Else it calculates all external commands -and sets `helm-external-commands-list'." - (helm-aif helm-external-commands-list - it - (setq helm-external-commands-list - (cl-loop - for dir in (split-string (getenv "PATH") path-separator) - when (and (file-exists-p dir) (file-accessible-directory-p dir)) - for lsdir = (cl-loop for i in (directory-files dir t) - for bn = (file-name-nondirectory i) - when (and (not (member bn completions)) - (not (file-directory-p i)) - (file-executable-p i)) - collect bn) - append lsdir into completions - finally return - (if sort (sort completions 'string-lessp) completions))))) - -(defun helm-run-or-raise (exe &optional file) - "Run asynchronously EXE or jump to the application window. -If EXE is already running just jump to his window if `helm-raise-command' -is non--nil. -When FILE argument is provided run EXE with FILE." - (let* ((real-com (car (split-string exe))) - (proc (if file (concat real-com " " file) real-com)) - process-connection-type) - (if (get-process proc) - (if helm-raise-command - (shell-command (format helm-raise-command real-com)) - (error "Error: %s is already running" real-com)) - (when (member real-com helm-external-commands-list) - (message "Starting %s..." real-com) - (if file - (start-process-shell-command - proc nil (format "%s %s" - real-com - (shell-quote-argument - (if (eq system-type 'windows-nt) - (helm-w32-prepare-filename file) - (expand-file-name file))))) - (start-process-shell-command proc nil real-com)) - (set-process-sentinel - (get-process proc) - (lambda (process event) - (when (and (string= event "finished\n") - helm-raise-command - (not (helm-get-pid-from-process-name real-com))) - (shell-command (format helm-raise-command "emacs"))) - (message "%s process...Finished." process)))) - (setq helm-external-commands-list - (cons real-com - (delete real-com helm-external-commands-list)))))) - -(defun helm-get-mailcap-for-file (filename) - "Get the command to use for FILENAME from mailcap files." - (mailcap-parse-mailcaps) - (let* ((ext (file-name-extension filename)) - (mime (when ext (mailcap-extension-to-mime ext))) - (result (when mime (mailcap-mime-info mime)))) - ;; If elisp file have no associations in .mailcap - ;; `mailcap-maybe-eval' is returned, in this case just return nil. - (when (stringp result) (helm-basename result)))) - -(defun helm-get-default-program-for-file (filename) - "Try to find a default program to open FILENAME. -Try first in `helm-external-programs-associations' and then in mailcap file -if nothing found return nil." - (let* ((ext (file-name-extension filename)) - (def-prog (assoc-default ext helm-external-programs-associations))) - (cond ((and def-prog (not (string= def-prog ""))) def-prog) - ((and helm-default-external-file-browser (file-directory-p filename)) - helm-default-external-file-browser) - (t (helm-get-mailcap-for-file filename))))) - -(defun helm-open-file-externally (file) - "Open FILE with an external program. -Try to guess which program to use with `helm-get-default-program-for-file'. -If not found or a prefix arg is given query the user which tool to use." - (let* ((fname (expand-file-name file)) - (collection (helm-external-commands-list-1 'sort)) - (def-prog (helm-get-default-program-for-file fname)) - (program (if (or helm-current-prefix-arg (not def-prog)) - ;; Prefix arg or no default program. - (prog1 - (helm-comp-read - "Program: " collection - :must-match t - :name "Open file Externally" - :del-input nil - :history helm-external-command-history) - ;; Always prompt to set this program as default. - (setq def-prog nil)) - ;; No prefix arg or default program exists. - def-prog))) - (unless (or def-prog ; Association exists, no need to record it. - ;; Don't try to record non--filenames associations (e.g urls). - (not (file-exists-p fname))) - (when - (y-or-n-p - (format - "Do you want to make `%s' the default program for this kind of files? " - program)) - (helm-aif (assoc (file-name-extension fname) - helm-external-programs-associations) - (setq helm-external-programs-associations - (delete it helm-external-programs-associations))) - (push (cons (file-name-extension fname) - (helm-read-string - "Program (Add args maybe and confirm): " program)) - helm-external-programs-associations) - (customize-save-variable 'helm-external-programs-associations - helm-external-programs-associations))) - (helm-run-or-raise program file) - (setq helm-external-command-history - (cons program - (delete program - (cl-loop for i in helm-external-command-history - when (executable-find i) collect i)))))) - -;;;###autoload -(defun helm-run-external-command (program) - "Preconfigured `helm' to run External PROGRAM asyncronously from Emacs. -If program is already running exit with error. -You can set your own list of commands with -`helm-external-commands-list'." - (interactive (list - (helm-comp-read - "RunProgram: " - (helm-external-commands-list-1 'sort) - :must-match t - :del-input nil - :name "External Commands" - :history helm-external-command-history))) - (helm-run-or-raise program) - (setq helm-external-command-history - (cons program (delete program - (cl-loop for i in helm-external-command-history - when (executable-find i) collect i))))) - - -(provide 'helm-external) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-external ends here diff --git a/elpa/helm-20191031.725/helm-files.el b/elpa/helm-20191031.725/helm-files.el deleted file mode 100644 index 4263ae77..00000000 --- a/elpa/helm-20191031.725/helm-files.el +++ /dev/null @@ -1,4861 +0,0 @@ -;;; helm-files.el --- helm file browser and related. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'cl-lib) -(require 'helm) -(require 'helm-types) -(require 'helm-utils) -(require 'helm-grep) -(require 'helm-help) -(require 'helm-locate) -(require 'helm-tags) -(require 'helm-buffers) -(eval-when-compile - (require 'thingatpt) - (require 'ffap) - (require 'dired-aux) - (require 'dired-x) - (require 'tramp) - (require 'image-dired)) - -(declare-function find-library-name "find-func.el" (library)) -(declare-function w32-shell-execute "ext:w32fns.c" (operation document &optional parameters show-flag)) -(declare-function gnus-dired-attach "ext:gnus-dired.el" (files-to-attach)) -(declare-function image-dired-display-image "image-dired.el" (file &optional original-size)) -(declare-function image-dired-update-property "image-dired.el" (prop value)) -(declare-function eshell-read-aliases-list "em-alias") -(declare-function eshell-send-input "esh-mode" (&optional use-region queue-p no-newline)) -(declare-function eshell-kill-input "esh-mode") -(declare-function eshell-bol "esh-mode") -(declare-function eshell-reset "esh-mode.el") -(declare-function eshell/cd "em-dirs.el") -(declare-function eshell-next-prompt "em-prompt.el") -(declare-function eshell-quote-argument "esh-arg.el") -(declare-function helm-ls-git-ls "ext:helm-ls-git") -(declare-function helm-hg-find-files-in-project "ext:helm-ls-hg") -(declare-function helm-gid "helm-id-utils.el") -(declare-function helm-find-1 "helm-find") -(declare-function helm-get-default-program-for-file "helm-external") -(declare-function helm-open-file-externally "helm-external") - -(defvar recentf-list) -(defvar helm-mm-matching-method) -(defvar dired-async-mode) -(defvar org-directory) - -(defgroup helm-files nil - "Files applications and libraries for Helm." - :group 'helm) - -(defcustom helm-tramp-verbose 0 - "Just like `tramp-verbose' but specific to helm. -When set to 0 don't show tramp messages in helm. -If you want to have the default tramp messages set it to 3." - :type 'integer - :group 'helm-files) - -(defcustom helm-ff-auto-update-initial-value nil - "Auto update when only one candidate directory is matched. -Default value when starting `helm-find-files' is nil to not confuse -new users. -For a better experience with `helm-find-files' set this to non--nil -and use C- to toggle it." - :group 'helm-files - :type 'boolean) - -(defcustom helm-ff-history-max-length 100 - "Number of elements shown in `helm-find-files' history." - :group 'helm-files - :type 'integer) - -(defcustom helm-ff-fuzzy-matching t - "Enable fuzzy matching for `helm-find-files' when non--nil. -See `helm-ff--transform-pattern-for-completion' for more info." - :group 'helm-files - :type 'boolean) - -(defcustom helm-ff-exif-data-program "exiftran" - "Program used to extract exif data of an image file." - :group 'helm-files - :type 'string) - -(defcustom helm-ff-exif-data-program-args "-d" - "Arguments used for `helm-ff-exif-data-program'." - :group 'helm-files - :type 'string) - -(defcustom helm-ff-newfile-prompt-p t - "Whether Prompt or not when creating new file. -This set `ffap-newfile-prompt'." - :type 'boolean - :group 'helm-files) - -(defcustom helm-ff-avfs-directory "~/.avfs" - "The default avfs directory, usually '~/.avfs'. -When this is set you will be able to expand archive filenames with `C-j' -inside an avfs directory mounted with mountavfs. -See ." - :type 'string - :group 'helm-files) - -(defcustom helm-ff-file-compressed-list '("gz" "bz2" "zip" "7z") - "Minimal list of compressed files extension." - :type '(repeat (choice string)) - :group 'helm-files) - -(defcustom helm-ff-printer-list nil - "A list of available printers on your system. -When non--nil let you choose a printer to print file. -Otherwise when nil the variable `printer-name' will be used. -On Unix based systems (lpstat command needed) you don't need to set this, -`helm-ff-find-printers' will find a list of available printers for you." - :type '(repeat (choice string)) - :group 'helm-files) - -(defcustom helm-ff-transformer-show-only-basename t - "Show only basename of candidates in `helm-find-files'. -This can be toggled at anytime from `helm-find-files' with \ -\\\\[helm-ff-run-toggle-basename]." - :type 'boolean - :group 'helm-files) - -(defcustom helm-ff-signal-error-on-dot-files t - "Signal error when file is `.' or `..' on file deletion when non--nil. -Default is non--nil. -WARNING: Setting this to nil is unsafe and can cause deletion of a whole tree." - :group 'helm-files - :type 'boolean) - -(defcustom helm-ff-search-library-in-sexp nil - "Search for library in `require' and `declare-function' sexp." - :group 'helm-files - :type 'boolean) - -(defcustom helm-tooltip-hide-delay 25 - "Hide tooltips automatically after this many seconds." - :group 'helm-files - :type 'integer) - -(defcustom helm-ff-file-name-history-use-recentf nil - "Use `recentf-list' instead of `file-name-history' in `helm-find-files'." - :group 'helm-files - :type 'boolean) - -(defcustom helm-ff-skip-boring-files nil - "Non--nil to skip boring files. - -I.e. the files matching regexps in `helm-boring-file-regexp-list'. -This take effect in `helm-find-files' and file completion used by `helm-mode' -i.e `helm-read-file-name'. -Note that when non-nil this will slow down slightly `helm-find-files'." - :group 'helm-files - :type 'boolean) - -(defcustom helm-ff-skip-git-ignored-files nil - "Non--nil to skip git ignored files. - -This take effect only in `helm-find-files'. -Check is not done on remote files. -Note that when non-nil this will slow down slightly `helm-find-files'." - :group 'helm-files - :type 'boolean) - -(defcustom helm-ff-candidate-number-limit 5000 - "The `helm-candidate-number-limit' for `helm-find-files' and friends. -Note that when going one level up with `\\\\[helm-find-files-up-one-level]' -The length of directory will be used instead if it is higher than this -value, this to avoid failing to preselect the previous directory/file if -this one is situated lower than `helm-ff-candidate-number-limit' num -candidate." - :group 'helm-files - :type 'integer) - -(defcustom helm-ff-up-one-level-preselect t - "Always preselect previous directory when going one level up. - -When non nil `candidate-number-limit' source value is modified -dynamically when going one level up if the position of previous -candidate in its directory is > to `helm-ff-candidate-number-limit'. - -This can be helpful to disable this and reduce -`helm-ff-candidate-number-limit' if you often navigate across very -large directories." - :group 'helm-files - :type 'boolean) - -(defcustom helm-files-save-history-extra-sources - '("Find" "Locate" "Recentf" - "Files from Current Directory" "File Cache") - "Extras source that save candidate to `file-name-history'." - :group 'helm-files - :type '(repeat (choice string))) - -(defcustom helm-find-files-before-init-hook nil - "Hook that run before initialization of `helm-find-files'." - :group 'helm-files - :type 'hook) - -(defcustom helm-find-files-after-init-hook nil - "Hook that run after initialization of `helm-find-files'." - :group 'helm-files - :type 'hook) - -(defcustom helm-find-files-bookmark-prefix "Helm-find-files: " - "bookmark name prefix of `helm-find-files' sessions." - :group 'helm-files - :type 'string) - -(defcustom helm-ff-guess-ffap-filenames nil - "Use ffap to guess local filenames at point in `helm-find-files'. -This doesn't disable url or mail at point, see -`helm-ff-guess-ffap-urls' for this." - :group 'helm-files - :type 'boolean) - -(defcustom helm-ff-guess-ffap-urls t - "Use ffap to guess local urls at point in `helm-find-files'. -This doesn't disable guessing filenames at point, -see `helm-ff-guess-ffap-filenames' for this. -See also `ffap-url-unwrap-remote' that may override this variable." - :group 'helm-files - :type 'boolean) - -(defcustom helm-ff-no-preselect nil - "When non--nil `helm-find-files' starts at root of current directory." - :group 'helm-files - :type 'boolean) - -(defcustom helm-ff-allow-non-existing-file-at-point nil - "Use file-at-point as initial input in `helm-find-files' even if it doesn't exists." - :group 'helm-files - :type 'boolean) - -(defcustom helm-find-files-ignore-thing-at-point nil - "Use only `default-directory' as default input in `helm-find-files'. -I.e text under cursor in `current-buffer' is ignored. -Note that when non-nil you will be unable to complete filename at point -in `current-buffer'." - :group 'helm-files - :type 'boolean) - -(defcustom helm-substitute-in-filename-stay-on-remote nil - "Don't switch back to local filesystem when expanding pattern with / or ~/." - :group 'helm-files - :type 'boolean) - -(defcustom helm-ff-goto-first-real-dired-exceptions '(dired-goto-file) - "Dired commands that are allowed moving to first real candidate." - :group 'helm-files - :type '(repeat (choice symbol))) - -(defcustom helm-mounted-network-directories nil - "A list of directories used for mounting remotes filesystem. - -When nil `helm-file-on-mounted-network-p' always return nil otherwise -it checks if a file is in one of these directories. - -Remote filesystem are generally mounted with sshfs." - :group 'helm-files - :type '(repeat string)) - -(defcustom helm-browse-project-default-find-files-fn - (cond ((executable-find "rg") - #'helm-browse-project-rg-find-files) - ((executable-find "ag") - #'helm-browse-project-ag-find-files) - (t #'helm-browse-project-walk-directory)) - "The default function to retrieve files in a non-vc directory. - -A function that takes a directory name as only arg." - :group 'helm-files - :type 'function) - -(defcustom helm-ff-kill-or-find-buffer-fname-fn - #'helm-ff-kill-or-find-buffer-fname - "Default function used to expand non-directory filenames in `helm-find-files'. - -This variable will take effect only in `helm-find-files', it affects -the behavior of persistent-action on filenames and non-existing -filenames. - -The default is to expand filename on first hit on -\\\\[helm-execute-persistent-action], pop buffer in other -window on second hit and finally kill this buffer on third hit, this -is very handy to create several new buffers, or when navigating, show -quickly the buffer of file to see its contents briefly before killing -it and continue navigating. - -However some users may not want this, so to disable this behavior just -set this to `ignore' function. - -Of course you can also write your own function to do something else." - :group 'helm-files - :type 'function) - -(defcustom helm-modes-using-escaped-strings - '(eshell-mode shell-mode term-mode) - "Modes that requires string's insertion to be escaped." - :group 'helm-files - :type '(repeat symbol)) - -(defcustom helm-ff-allow-recursive-deletes nil - "when 'always don't prompt for recursive deletion of directories. -When nil, will ask for recursive deletion. -Note that when deleting multiple directories you can answer ! when -prompted to avoid beeing asked for next directories, so it is probably -better to not modify this variable." - :group 'helm-files - :type '(choice - (const :tag "Delete non-empty directories" t) - (const :tag "Confirm for each directory" nil))) - -(defcustom helm-ff-delete-files-function #'helm-delete-marked-files - "The function to use by default to delete files. - -Default is to delete files synchronously, other choice is to delete -files asynchronously. - -BE AWARE that when deleting async you will not be warned about -recursive deletion of directories, IOW non empty directories will be -deleted with no warnings in background!!! - -It is the function that will be used when using `\\\\[helm-ff-run-delete-file]' -from `helm-find-files'." - :group 'helm-files - :type '(choice (function :tag "Delete files synchronously." - helm-delete-marked-files) - (function :tag "Delete files asynchronously." - helm-delete-marked-files-async))) - -(defcustom helm-trash-remote-files nil - "Allow trashing remote files when non-nil. - -Trashing remote files with tramp doesn't work out of the box unless -'trash-cli' package is installed, it is why trashing remote files from -helm is disabled by default. - -Tramp is using external 'trash' command in its `delete-file' and -`delete-directory' handlers when using `delete-by-moving-to-trash', -which is documented nowhere in Emacs. - -If you want to enable this you will have to install the 'trash' command -on remote (and/or locally if you want to trash as root), on Ubuntu -based distribution it is 'trash-cli'." - :group 'helm-files - :type 'boolean) - -(defcustom helm-list-directory-function - (cl-case system-type - (gnu/linux #'helm-list-dir-external) - (berkeley-unix #'helm-list-dir-lisp) - (windows-nt #'helm-list-dir-lisp) - (t #'helm-list-dir-lisp)) - "The function used in `helm-find-files' to list remote directories. - -Actually helm provides two functions to do this: `helm-list-dir-lisp' -and `helm-list-dir-external'. - -Using `helm-list-dir-external' will provides a similar display to what -provided with local files i.e. colorized symlinks, executables files -etc... whereas using `helm-list-dir-lisp' will allow colorizing only -directories but is more portable. - -NOTE: `helm-list-dir-external' needs ls and awk as dependencies. -Also the ls version installed on the remote side should support the -same arguments as the GNU/ls version that are -A -1 -F -b and -Q. -So even if you are using a GNU/ls version locally and you want to -connect e.g. on a Freebsd server you may have failures due to the -incompatible ls version installed on remote server. -In such case use `helm-list-dir-lisp' which work everywhere but is -slower and less featured (only directories colorized)." - :type 'function - :group 'helm-files) - -(defcustom helm-ff-initial-sort-method nil - "Sort method to use when initially listing a directory. -Note that this doesn't affect the listing when matching inside the -directory (i.e. filenames)." - :group 'helm-files - :type '(choice - (const :tag "alphabetically" nil) - (const :tag "newest" newest) - (const :tag "size" size))) - -(defcustom helm-ff-rotate-image-program "exiftran" - "External program used to rotate images." - :group 'helm-files - :type '(choice - (const :tag "Mogrify" "mogrify") - (const :tag "Exiftran" "exiftran") - (const :tag "Jpegtran" "jpegtran"))) - -(defcustom helm-ff-rotate-image-switch '("-i") - "Options used with `helm-ff-rotate-image-program'. -If you are using Mogrify or Jpegtran mandatory option is \"-rotate\", -with Exiftran mandatory option is \"-i\"." - :group 'helm-files - :type '(repeat string)) - - -;;; Faces -;; -;; -(defgroup helm-files-faces nil - "Customize the appearance of helm-files." - :prefix "helm-" - :group 'helm-files - :group 'helm-faces) - -(defface helm-ff-prefix - '((t (:background "yellow" :foreground "black"))) - "Face used to prefix new file or url paths in `helm-find-files'." - :group 'helm-files-faces) - -(defface helm-ff-executable - '((t (:foreground "green"))) - "Face used for executable files in `helm-find-files'." - :group 'helm-files-faces) - -(defface helm-ff-suid - '((t (:background "red" :foreground "white"))) - "Face used for suid files in `helm-find-files'." - :group 'helm-files-faces) - -(defface helm-ff-directory - '((t (:foreground "DarkRed" :background "LightGray"))) - "Face used for directories in `helm-find-files'." - :group 'helm-files-faces) - -(defface helm-ff-dotted-directory - '((t (:foreground "black" :background "DimGray"))) - "Face used for dotted directories in `helm-find-files'." - :group 'helm-files-faces) - -(defface helm-ff-dotted-symlink-directory - '((t (:foreground "DarkOrange" :background "DimGray"))) - "Face used for dotted symlinked directories in `helm-find-files'." - :group 'helm-files-faces) - -(defface helm-ff-symlink - '((t :inherit font-lock-comment-face)) - "Face used for symlinks in `helm-find-files'." - :group 'helm-files-faces) - -(defface helm-ff-invalid-symlink - '((t (:foreground "black" :background "red"))) - "Face used for invalid symlinks in `helm-find-files'." - :group 'helm-files-faces) - -(defface helm-ff-denied - '((t (:foreground "red" :background "black"))) - "Face used for non accessible files in `helm-find-files'." - :group 'helm-files-faces) - -(defface helm-ff-file - '((t (:inherit font-lock-builtin-face))) - "Face used for file names in `helm-find-files'." - :group 'helm-files-faces) - -(defface helm-ff-truename - '((t (:inherit font-lock-string-face))) - "Face used for symlink truenames in `helm-find-files'." - :group 'helm-files-faces) - -(defface helm-ff-dirs - '((t (:inherit font-lock-function-name-face))) - "Face used for file names in recursive dirs completion in `helm-find-files'." - :group 'helm-files-faces) - -(defface helm-ff-socket - '((t (:foreground "DeepPink"))) - "Face used for socket files in `helm-find-files'." - :group 'helm-files-faces) - -(defface helm-ff-pipe - '((t (:foreground "yellow" :background "black"))) - "Face used for named pipes and character device files in `helm-find-files'." - :group 'helm-files-faces) - -(defface helm-history-deleted - '((t (:inherit helm-ff-invalid-symlink))) - "Face used for deleted files in `file-name-history'." - :group 'helm-files-faces) - -(defface helm-history-remote - '((t (:foreground "Indianred1"))) - "Face used for remote files in `file-name-history'." - :group 'helm-files-faces) - -(defface helm-delete-async-message - '((t (:foreground "yellow"))) - "Face used for mode-line message." - :group 'helm-files-faces) - -;;; Helm-find-files - The helm file browser. -;; -;; Keymaps - -(defvar helm-find-files-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "RET") 'helm-ff-RET) - (define-key map (kbd "C-]") 'helm-ff-run-toggle-basename) - (define-key map (kbd "C-x C-f") 'helm-ff-run-locate) - (define-key map (kbd "C-x C-d") 'helm-ff-run-browse-project) - (define-key map (kbd "C-x r m") 'helm-ff-bookmark-set) - (define-key map (kbd "C-x r b") 'helm-find-files-switch-to-bookmark) - (define-key map (kbd "C-x C-q") 'helm-ff-run-marked-files-in-dired) - (define-key map (kbd "C-s") 'helm-ff-run-grep) - (define-key map (kbd "M-g s") 'helm-ff-run-grep) - (define-key map (kbd "M-g p") 'helm-ff-run-pdfgrep) - (define-key map (kbd "M-g z") 'helm-ff-run-zgrep) - (define-key map (kbd "M-g a") 'helm-ff-run-grep-ag) - (define-key map (kbd "M-g g") 'helm-ff-run-git-grep) - (define-key map (kbd "M-g i") 'helm-ff-run-gid) - (define-key map (kbd "M-.") 'helm-ff-run-etags) - (define-key map (kbd "M-R") 'helm-ff-run-rename-file) - (define-key map (kbd "M-C") 'helm-ff-run-copy-file) - (define-key map (kbd "M-B") 'helm-ff-run-byte-compile-file) - (define-key map (kbd "M-L") 'helm-ff-run-load-file) - (define-key map (kbd "M-S") 'helm-ff-run-symlink-file) - (define-key map (kbd "M-Y") 'helm-ff-run-relsymlink-file) - (define-key map (kbd "M-H") 'helm-ff-run-hardlink-file) - (define-key map (kbd "M-D") 'helm-ff-run-delete-file) - (define-key map (kbd "M-K") 'helm-ff-run-kill-buffer-persistent) - (define-key map (kbd "M-T") 'helm-ff-run-touch-files) - (define-key map (kbd "C-c d") 'helm-ff-persistent-delete) - (define-key map (kbd "M-e") 'helm-ff-run-switch-to-eshell) - (define-key map (kbd "C-c i") 'helm-ff-run-complete-fn-at-point) - (define-key map (kbd "C-c o") 'helm-ff-run-switch-other-window) - (define-key map (kbd "C-c C-o") 'helm-ff-run-switch-other-frame) - (define-key map (kbd "C-c C-x") 'helm-ff-run-open-file-externally) - (define-key map (kbd "C-c C-v") 'helm-ff-run-preview-file-externally) - (define-key map (kbd "C-c X") 'helm-ff-run-open-file-with-default-tool) - (define-key map (kbd "M-!") 'helm-ff-run-eshell-command-on-file) - (define-key map (kbd "M-@") 'helm-ff-run-query-replace-fnames-on-marked) - (define-key map (kbd "M-%") 'helm-ff-run-query-replace) - (define-key map (kbd "C-M-%") 'helm-ff-run-query-replace-regexp) - (define-key map (kbd "C-c =") 'helm-ff-run-ediff-file) - (define-key map (kbd "M-=") 'helm-ff-run-ediff-merge-file) - (define-key map (kbd "M-p") 'helm-find-files-history) - (define-key map (kbd "C-c h") 'helm-ff-file-name-history) - (define-key map (kbd "M-i") 'helm-ff-properties-persistent) - (define-key map (kbd "C-}") 'helm-narrow-window) - (define-key map (kbd "C-{") 'helm-enlarge-window) - (define-key map (kbd "C-") 'helm-ff-run-toggle-auto-update) - (define-key map (kbd "C-c ") 'helm-ff-run-toggle-auto-update) - (define-key map (kbd "C-c C-a") 'helm-ff-run-mail-attach-files) - (define-key map (kbd "C-c p") 'helm-ff-run-print-file) - (define-key map (kbd "C-c /") 'helm-ff-run-find-sh-command) - ;; Next 2 have no effect if candidate is not an image file. - (define-key map (kbd "M-l") 'helm-ff-rotate-left-persistent) - (define-key map (kbd "M-r") 'helm-ff-rotate-right-persistent) - (define-key map (kbd "C-l") 'helm-find-files-up-one-level) - (define-key map (kbd "C-r") 'helm-find-files-down-last-level) - (define-key map (kbd "C-c r") 'helm-ff-run-find-file-as-root) - (define-key map (kbd "C-x C-v") 'helm-ff-run-find-alternate-file) - (define-key map (kbd "C-c @") 'helm-ff-run-insert-org-link) - (define-key map (kbd "S-") 'helm-ff-sort-alpha) - (define-key map (kbd "S-") 'helm-ff-sort-by-newest) - (define-key map (kbd "S-") 'helm-ff-sort-by-size) - (helm-define-key-with-subkeys map (kbd "DEL") ?\d 'helm-ff-delete-char-backward - '((C-backspace . helm-ff-run-toggle-auto-update) - ([C-c DEL] . helm-ff-run-toggle-auto-update)) - nil 'helm-ff-delete-char-backward--exit-fn) - (when (fboundp 'tab-bar-mode) - (define-key map (kbd "C-c C-t") 'helm-ff-find-file-other-tab)) - map) - "Keymap for `helm-find-files'.") - -(defvar helm-read-file-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "") 'helm-cr-empty-string) - (define-key map (kbd "M-RET") 'helm-cr-empty-string) - (define-key map (kbd "C-]") 'helm-ff-run-toggle-basename) - (define-key map (kbd "C-.") 'helm-find-files-up-one-level) - (define-key map (kbd "C-l") 'helm-find-files-up-one-level) - (define-key map (kbd "C-r") 'helm-find-files-down-last-level) - (define-key map (kbd "C-c h") 'helm-ff-file-name-history) - (define-key map (kbd "C-") 'helm-ff-run-toggle-auto-update) - (define-key map (kbd "C-c ") 'helm-ff-run-toggle-auto-update) - (helm-define-key-with-subkeys map (kbd "DEL") ?\d 'helm-ff-delete-char-backward - '((C-backspace . helm-ff-run-toggle-auto-update) - ([C-c DEL] . helm-ff-run-toggle-auto-update)) - nil 'helm-ff-delete-char-backward--exit-fn) - map) - "Keymap for `helm-read-file-name'.") - -(defcustom helm-ff-lynx-style-map nil - "Use arrow keys to navigate with `helm-find-files'. -Note that if you define this variable with `setq' your change will -have no effect, use customize instead." - :group 'helm-files - :type 'boolean - :set (lambda (var val) - (set var val) - (if val - (progn - (define-key helm-find-files-map (kbd "") 'helm-execute-persistent-action) - (define-key helm-find-files-map (kbd "") 'helm-find-files-up-one-level) - (define-key helm-read-file-map (kbd "") 'helm-execute-persistent-action) - (define-key helm-read-file-map (kbd "") 'helm-find-files-up-one-level)) - (define-key helm-find-files-map (kbd "") nil) - (define-key helm-find-files-map (kbd "") nil) - (define-key helm-read-file-map (kbd "") nil) - (define-key helm-read-file-map (kbd "") nil)))) - -(defcustom helm-ff-DEL-up-one-level-maybe nil - "Use DEL to maybe go up one level when non nil. - -Going up one level works only when pattern is a directory endings with -\"/\", otherwise this command delete char backward. - -When nil always delete char backward." - :group 'helm-files - :type 'boolean) - -;; Internal. -(defvar helm-find-files-doc-header " (\\\\[helm-find-files-up-one-level]: Go up one level)" - "*The doc that is inserted in the Name header of a find-files or dired source.") -(defvar helm-ff-auto-update-flag nil - "Internal, flag to turn on/off auto-update in `helm-find-files'. -Don't set it directly, use instead `helm-ff-auto-update-initial-value'.") -(defvar helm-ff-last-expanded nil - "Store last expanded directory or file.") -(defvar helm-ff-default-directory nil) -(defvar helm-ff-history nil) -(defvar helm-ff-cand-to-mark nil) -(defvar helm-ff-url-regexp - "\\`\\(news\\(post\\)?:\\|nntp:\\|mailto:\\|file:\\|\\(ftp\\|https?\\|telnet\\|gopher\\|www\\|wais\\):/?/?\\).*" - "Same as `ffap-url-regexp' but match earlier possible url.") -;; helm-tramp-file-name-regexp is based on old version of -;; tramp-file-name-regexp i.e. "\\`/\\([^[/:]+\\|[^/]+]\\):" but it -;; seems it is wrong and a simpler regexp is enough, let's try it and -;; watch out! -(defvar helm-tramp-file-name-regexp "\\`/\\([^/:|]+\\):") -(defvar helm-marked-buffer-name "*helm marked*") -(defvar helm-ff--auto-update-state nil) -(defvar helm-ff--deleting-char-backward nil) -(defvar helm-multi-files--toggle-locate nil) -(defvar helm-ff--move-to-first-real-candidate t) -(defvar helm-find-files--toggle-bookmark nil) -(defvar helm-ff--tramp-methods nil) -(defvar helm-ff--directory-files-hash (make-hash-table :test 'equal)) -(defvar helm-ff-history-buffer-name "*helm-find-files history*") - -;;; Helm-find-files -;; -;; -(defcustom helm-find-files-actions - (helm-make-actions - "Find File" 'helm-find-file-or-marked - "Find file in Dired" 'helm-point-file-in-dired - "View file" 'view-file - "Query replace fnames on marked `M-@'" 'helm-ff-query-replace-fnames-on-marked - "Marked files in dired `C-x C-q, C-u wdired'" 'helm-marked-files-in-dired - "Query replace contents on marked `M-%'" 'helm-ff-query-replace - "Query replace regexp contents on marked `C-M-%'" 'helm-ff-query-replace-regexp - "Attach file(s) to mail buffer `C-c C-a'" 'helm-ff-mail-attach-files - "Serial rename files" 'helm-ff-serial-rename - "Serial rename by symlinking files" 'helm-ff-serial-rename-by-symlink - "Serial rename by copying files" 'helm-ff-serial-rename-by-copying - "Open file with default tool" 'helm-open-file-with-default-tool - "Find file in hex dump" 'hexl-find-file - "Browse project `C-x C-d'" 'helm-ff-browse-project - "Complete at point `C-c i'" 'helm-insert-file-name-completion-at-point - "Insert as org link `C-c @'" 'helm-files-insert-as-org-link - "Find shell command `C-c /'" 'helm-ff-find-sh-command - "Add marked files to file-cache" 'helm-ff-cache-add-file - "Open file externally `C-c C-x, C-u to choose'" 'helm-open-file-externally - "Grep File(s) `C-s, C-u Recurse'" 'helm-find-files-grep - "Grep current directory with AG `M-g a, C-u select type'" 'helm-find-files-ag - "Git grep `M-g g, C-u from root'" 'helm-ff-git-grep - "Zgrep File(s) `M-g z, C-u Recurse'" 'helm-ff-zgrep - "Gid `M-g i'" 'helm-ff-gid - "Switch to Eshell `M-e'" 'helm-ff-switch-to-eshell - "Etags `M-., C-u reload tag file'" 'helm-ff-etags-select - "Eshell command on file(s) `M-!, C-u take all marked as arguments.'" - 'helm-find-files-eshell-command-on-file - "Find file as root `C-c r'" 'helm-find-file-as-root - "Find alternate file `C-x C-v'" 'find-alternate-file - "Ediff File `C-c ='" 'helm-find-files-ediff-files - "Ediff Merge File `M-='" 'helm-find-files-ediff-merge-files - (lambda () (format "Delete File(s)%s `M-D' (C-u reverse trash)" - (if (eq helm-ff-delete-files-function - 'helm-delete-marked-files-async) - " async" ""))) - 'helm-ff-delete-files - "Touch File(s) `M-T'" 'helm-ff-touch-files - "Copy file(s) `M-C, C-u to follow'" 'helm-find-files-copy - "Rename file(s) `M-R, C-u to follow'" 'helm-find-files-rename - "Backup files" 'helm-find-files-backup - "Symlink files(s) `M-S, C-u to follow'" 'helm-find-files-symlink - "Relsymlink file(s) `M-Y, C-u to follow'" 'helm-find-files-relsymlink - "Hardlink file(s) `M-H, C-u to follow'" 'helm-find-files-hardlink - "Find file other window `C-c o'" 'helm-find-files-other-window - "Find file other frame `C-c C-o'" 'find-file-other-frame - (lambda () (and (fboundp 'tab-bar-mode) - "Find file other tab `C-c C-t'")) - 'find-file-other-tab - "Print File `C-c p, C-u to refresh'" 'helm-ff-print - "Locate `C-x C-f, C-u to specify locate db'" 'helm-ff-locate) - "Actions for `helm-find-files'." - :group 'helm-files - :type '(alist :key-type string :value-type function)) - -(defvar helm-source-find-files nil - "The main source to browse files. -Should not be used among other sources.") - -(defclass helm-source-ffiles (helm-source-sync) - ((header-name - :initform (lambda (name) - (concat name (substitute-command-keys - helm-find-files-doc-header)))) - (init - :initform (lambda () - (setq helm-ff-auto-update-flag - helm-ff-auto-update-initial-value) - (setq helm-ff--auto-update-state - helm-ff-auto-update-flag) - (helm-set-local-variable 'bookmark-make-record-function - #'helm-ff-make-bookmark-record) - (require 'helm-external))) - (candidates :initform 'helm-find-files-get-candidates) - (filtered-candidate-transformer - :initform '((lambda (candidates _source) - (cl-loop for f in candidates - for ff = (helm-ff-filter-candidate-one-by-one f) - when ff collect ff)) - helm-ff-sort-candidates)) - (persistent-action-if :initform 'helm-find-files-persistent-action-if) - (persistent-help :initform "Hit1 Expand Candidate, Hit2 or (C-u) Find file") - (help-message :initform 'helm-ff-help-message) - (mode-line :initform (list "File(s)" helm-mode-line-string)) - (volatile :initform t) - (cleanup :initform 'helm-find-files-cleanup) - (migemo :initform t) - (nohighlight :initform t) - (keymap :initform helm-find-files-map) - (candidate-number-limit :initform 'helm-ff-candidate-number-limit) - (action-transformer - :initform 'helm-find-files-action-transformer) - (action :initform 'helm-find-files-actions) - (before-init-hook :initform 'helm-find-files-before-init-hook) - (after-init-hook :initform 'helm-find-files-after-init-hook) - (group :initform 'helm-files))) - -;; Bookmark handlers. -;; -(defun helm-ff-make-bookmark-record () - "The `bookmark-make-record-function' for `helm-find-files'." - (with-helm-buffer - `((filename . ,helm-ff-default-directory) - (presel . ,(helm-get-selection)) - (handler . helm-ff-bookmark-jump)))) - -(defun helm-ff-bookmark-jump (bookmark) - "bookmark handler for `helm-find-files'." - (let ((fname (bookmark-prop-get bookmark 'filename)) - (presel (bookmark-prop-get bookmark 'presel))) - ;; Force tramp connection with `file-directory-p' before lauching - ;; hff otherwise the directory name is inserted on top before - ;; tramp starts and display candidates. FNAME is here always a - ;; directory. - (when (file-directory-p fname) - (helm-find-files-1 fname (if helm-ff-transformer-show-only-basename - (concat "^" (regexp-quote (helm-basename presel))) - (regexp-quote presel)))))) - -(defun helm-ff-bookmark-set () - "Record `helm-find-files' session in bookmarks." - (interactive) - (with-helm-alive-p - (with-helm-buffer - (bookmark-set - (concat helm-find-files-bookmark-prefix - (abbreviate-file-name helm-ff-default-directory)))) - (message "Helm find files session bookmarked! "))) -(put 'helm-ff-bookmark-set 'helm-only t) - -(defcustom helm-dwim-target nil - "Default target directory for file actions. - -Define the directory where you want to start navigating for the target -directory when copying, renaming etc... You can use the -`default-directory' of `next-window', the current -`default-directory' or have completion on all the directories -belonging to each window." - :group 'helm-files - :type '(radio :tag "Define default target directory for file actions." - (const :tag "Directory belonging to next window" next-window) - (const :tag "Completion on directories belonging to each window" completion) - (const :tag "Use initial directory or `default-directory'" nil))) - -(defun helm-dwim-target-directory () - "Try to return a suitable directory according to `helm-dwim-target'." - (with-helm-current-buffer - (let* ((wins (remove (get-buffer-window helm-marked-buffer-name) - (window-list))) - (num-windows (length wins))) - (expand-file-name - (cond ((and (> num-windows 1) - (eq helm-dwim-target 'completion)) - (helm-comp-read "Browse target starting from: " - (append (list (or (car-safe helm-ff-history) - default-directory) - default-directory) - (cl-loop for w in wins collect - (with-selected-window w - default-directory))))) - ((and (> num-windows 1) - (eq helm-dwim-target 'next-window)) - (with-selected-window (next-window) - default-directory)) - ((or (= num-windows 1) - (null helm-dwim-target)) - ;; Using the car of *ff-history allow - ;; staying in the directory visited instead of - ;; current. - (or (car-safe helm-ff-history) default-directory))))))) - -(defun helm-ff--count-and-collect-dups (files) - (cl-loop with dups = (make-hash-table :test 'equal) - for f in files - for file = (if (file-directory-p f) - (concat (helm-basename f) "/") - (helm-basename f)) - for count = (gethash file dups) - if count do (puthash file (1+ count) dups) - else do (puthash file 1 dups) - finally return (cl-loop for k being the hash-keys in dups - using (hash-value v) - if (> v 1) - collect (format "%s(%s)" k v) - else - collect k))) - -(defun helm-find-files-do-action (action) - "Generic function for creating actions from `helm-source-find-files'. -ACTION must be an action supported by `helm-dired-action'." - (require 'dired-async) - (let* ((ifiles (mapcar 'expand-file-name ; Allow modify '/foo/.' -> '/foo' - (helm-marked-candidates :with-wildcard t))) - (cand (helm-get-selection)) ; Target - (prefarg helm-current-prefix-arg) - (prompt (format "%s %s file(s) %s: " - (if (and (and (fboundp 'dired-async-mode) - dired-async-mode) - (null prefarg)) - (concat "Async " (symbol-name action)) - (capitalize (symbol-name action))) - (length ifiles) - (if (memq action '(symlink relsymlink hardlink)) - "from" "to"))) - helm-ff--move-to-first-real-candidate - helm-display-source-at-screen-top ; prevent setting window-start. - helm-ff-auto-update-initial-value - ;; It is not possible to rename a file to a boring name when - ;; helm-ff-skip-boring-files is enabled - helm-ff-skip-boring-files - ;; If HFF is using a frame use a frame as well. - (helm-actions-inherit-frame-settings t) - helm-use-frame-when-more-than-two-windows - (dest (with-helm-display-marked-candidates - helm-marked-buffer-name - (helm-ff--count-and-collect-dups ifiles) - (with-helm-current-buffer - (helm-read-file-name - prompt - :preselect (unless (cdr ifiles) - (concat - "^" - (regexp-quote - (if helm-ff-transformer-show-only-basename - (helm-basename cand) cand)))) - :initial-input (helm-dwim-target-directory) - :history (helm-find-files-history nil :comp-read nil))))) - (dest-dir-p (file-directory-p dest)) - (dest-dir (helm-basedir dest))) - (unless (or dest-dir-p (file-directory-p dest-dir)) - (when (y-or-n-p (format "Create directory `%s'? " dest-dir)) - (make-directory dest-dir t))) - (helm-dired-action - dest :files ifiles :action action :follow prefarg))) - -(defun helm-find-files-copy (_candidate) - "Copy files from `helm-find-files'." - (helm-find-files-do-action 'copy)) - -(defun helm-find-files-backup (_candidate) - "Backup files from `helm-find-files'. -This reproduce the behavior of \"cp --backup=numbered from to\"." - (cl-assert (and (fboundp 'dired-async-mode) dired-async-mode) nil - "Backup only available when `dired-async-mode' is enabled") - (helm-find-files-do-action 'backup)) - -(defun helm-find-files-rename (_candidate) - "Rename files from `helm-find-files'." - (helm-find-files-do-action 'rename)) - -(defun helm-find-files-symlink (_candidate) - "Symlink files from `helm-find-files'." - (helm-find-files-do-action 'symlink)) - -(defun helm-find-files-relsymlink (_candidate) - "Relsymlink files from `helm-find-files'." - (helm-find-files-do-action 'relsymlink)) - -(defun helm-find-files-hardlink (_candidate) - "Hardlink files from `helm-find-files'." - (helm-find-files-do-action 'hardlink)) - -(defun helm-find-files-other-window (_candidate) - "Keep current-buffer and open files in separate windows. -When a prefix arg is detected files are opened in a vertical windows -layout." - (let* ((files (helm-marked-candidates)) - (buffers (mapcar 'find-file-noselect files))) - (helm-window-show-buffers buffers t))) - -(defun helm-find-files-byte-compile (_candidate) - "Byte compile elisp files from `helm-find-files'." - (let ((files (helm-marked-candidates :with-wildcard t)) - (parg helm-current-prefix-arg)) - (cl-loop for fname in files - do (byte-compile-file fname parg)))) - -(defun helm-find-files-load-files (_candidate) - "Load elisp files from `helm-find-files'." - (let ((files (helm-marked-candidates :with-wildcard t))) - (cl-loop for fname in files - do (load fname)))) - -(defun helm-find-files-ediff-files-1 (candidate &optional merge) - "Generic function to ediff/merge files in `helm-find-files'." - (let* ((helm-dwim-target 'next-window) - (bname (helm-basename candidate)) - (marked (helm-marked-candidates :with-wildcard t)) - (prompt (if merge "Ediff Merge `%s' With File: " - "Ediff `%s' With File: ")) - (fun (if merge 'ediff-merge-files 'ediff-files)) - (input (helm-dwim-target-directory)) - (presel (if helm-ff-transformer-show-only-basename - (helm-basename candidate) - (expand-file-name - (helm-basename candidate) - input)))) - (if (= (length marked) 2) - (funcall fun (car marked) (cadr marked)) - (funcall fun candidate (helm-read-file-name - (format prompt bname) - :initial-input input - :preselect presel))))) - -(defun helm-find-files-ediff-files (candidate) - (helm-find-files-ediff-files-1 candidate)) - -(defun helm-find-files-ediff-merge-files (candidate) - (helm-find-files-ediff-files-1 candidate 'merge)) - -(defun helm-find-files-grep (_candidate) - "Default action to grep files from `helm-find-files'." - (helm-do-grep-1 (helm-marked-candidates :with-wildcard t) - helm-current-prefix-arg)) - -(defun helm-ff-git-grep (_candidate) - "Default action to git-grep `helm-ff-default-directory'." - (helm-grep-git-1 helm-ff-default-directory helm-current-prefix-arg)) - -(defun helm-find-files-ag (_candidate) - (helm-grep-ag helm-ff-default-directory - helm-current-prefix-arg)) - -(defun helm-ff-zgrep (_candidate) - "Default action to zgrep files from `helm-find-files'." - (helm-ff-zgrep-1 (helm-marked-candidates :with-wildcard t) helm-current-prefix-arg)) - -(defun helm-ff-pdfgrep (_candidate) - "Default action to pdfgrep files from `helm-find-files'." - (let* ((recurse nil) - (cands (cl-loop for file in (helm-marked-candidates :with-wildcard t) - for dir = (file-directory-p file) - when dir do (setq recurse t) - when (or dir - (string= (file-name-extension file) "pdf") - (string= (file-name-extension file) "PDF")) - collect file))) - (when cands - (helm-do-pdfgrep-1 cands recurse)))) - -(defun helm-ff-etags-select (candidate) - "Default action to jump to etags from `helm-find-files'." - (when (get-buffer helm-action-buffer) - (kill-buffer helm-action-buffer)) - (let* ((source-name (assoc-default 'name (helm-get-current-source))) - (default-directory (if (string= source-name "Find Files") - helm-ff-default-directory - (file-name-directory candidate)))) - (helm-etags-select helm-current-prefix-arg))) - -(defvar eshell-command-aliases-list nil) -(defvar helm-eshell-command-on-file-input-history nil) -(cl-defun helm-find-files-eshell-command-on-file-1 (&optional map) - "Run `eshell-command' on CANDIDATE or marked candidates. -This is done possibly with an eshell alias, if no alias found, you can type in -an eshell command. - -Only aliases accepting a file as argument at the end of command line -are collected, i.e aliases ending with \"$1\" or \"$*\". - -Basename of CANDIDATE can be a wild-card. -e.g you can do \"eshell-command command *.el\" -Where \"*.el\" is the CANDIDATE. - -It is possible to do eshell-command command -like this: \"command %s some more args\". - -If MAP is given run `eshell-command' on all marked files at once, -Otherwise, run `eshell-command' on each marked files. -In other terms, with a prefix arg do on the three marked files -\"foo\" \"bar\" \"baz\": - -\"eshell-command command foo bar baz\" - -otherwise do - -\"eshell-command command foo\" -\"eshell-command command bar\" -\"eshell-command command baz\" - -Note: -You have to setup some aliases in eshell with the `alias' command or -by editing yourself the file `eshell-aliases-file' to make this -working." - (require 'em-alias) (eshell-read-aliases-list) - (when (or eshell-command-aliases-list - (y-or-n-p "No eshell aliases found, run eshell-command without alias anyway? ")) - (let* ((cand-list (helm-marked-candidates :with-wildcard t)) - (default-directory (or helm-ff-default-directory - ;; If candidate is an url *-ff-default-directory is nil - ;; so keep value of default-directory. - default-directory)) - helm-display-source-at-screen-top - (helm-actions-inherit-frame-settings t) - helm-use-frame-when-more-than-two-windows - (command (with-helm-display-marked-candidates - helm-marked-buffer-name - (helm-ff--count-and-collect-dups - (mapcar 'helm-basename cand-list)) - (with-helm-current-buffer - (helm-comp-read - "Command: " - (cl-loop for (a c) in (eshell-read-aliases-list) - ;; Positional arguments may be double - ;; quoted (Issue #1881). - when (string-match "[\"]?.*\\(\\$1\\|\\$\\*\\)[\"]?\\'" c) - collect (propertize a 'help-echo c) into ls - finally return (sort ls 'string<)) - :buffer "*helm eshell on file*" - :name "Eshell command" - :mode-line - '("Eshell alias" - "C-h m: Help, \\[universal-argument]: Insert output at point") - :help-message 'helm-esh-help-message - :input-history - 'helm-eshell-command-on-file-input-history)))) - (alias-value (car (assoc-default command eshell-command-aliases-list))) - cmd-line) - (if (or (equal helm-current-prefix-arg '(16)) - (equal map '(16))) - ;; Two time C-u from `helm-comp-read' mean print to current-buffer. - ;; i.e `eshell-command' will use this value. - (setq current-prefix-arg '(16)) - ;; Else reset the value of `current-prefix-arg' - ;; to avoid printing in current-buffer. - (setq current-prefix-arg nil)) - (if (and (or - ;; One prefix-arg have been passed before `helm-comp-read'. - ;; If map have been set with C-u C-u (value == '(16)) - ;; ignore it. - (and map (equal map '(4))) - ;; One C-u from `helm-comp-read'. - (equal helm-current-prefix-arg '(4)) - ;; An alias that finish with $* - (and alias-value - ;; If command is an alias be sure it accept - ;; more than one arg i.e $*. - (string-match "\\$\\*$" alias-value))) - (cdr cand-list)) - - ;; Run eshell-command with ALL marked files as arguments. - ;; This wont work on remote files, because tramp handlers depends - ;; on `default-directory' (limitation). - (let ((mapfiles (mapconcat 'eshell-quote-argument cand-list " "))) - (if (string-match "%s" command) - (setq cmd-line (format command mapfiles)) ; See [1] - (setq cmd-line (format "%s %s" command mapfiles))) - (eshell-command cmd-line)) - - ;; Run eshell-command on EACH marked files. - ;; To work with tramp handler we have to call - ;; COMMAND on basename of each file, using - ;; its basedir as `default-directory'. - (cl-loop for f in cand-list - for n from 1 - for dir = (and (not (string-match helm--url-regexp f)) - (helm-basedir f)) - ;; We can use basename here as the command will run - ;; under default-directory. - ;; This allow running e.g. "tar czvf test.tar.gz - ;; %s/*" without creating an archive expanding from /home. - for file = (eshell-quote-argument (helm-basename f)) - ;; \@ => placeholder for file without extension. - ;; \# => placeholder for incremental number. - for fcmd = (replace-regexp-in-string - "\\\\@" (regexp-quote (file-name-sans-extension file)) - (replace-regexp-in-string - "\\\\#" (format "%03d" n) command)) - for com = (if (string-match "%s" fcmd) - ;; [1] This allow to enter other args AFTER filename - ;; i.e - (format fcmd file) - (format "%s %s" fcmd file)) - do (let ((default-directory (or dir default-directory))) - (eshell-command com))))))) - -(defun helm-find-files-eshell-command-on-file (_candidate) - "Run `eshell-command' on CANDIDATE or marked candidates. -See `helm-find-files-eshell-command-on-file-1' for more info." - (helm-find-files-eshell-command-on-file-1 helm-current-prefix-arg)) - -(defun helm-ff-switch-to-eshell (_candidate) - "Switch to eshell and cd to `helm-ff-default-directory'. - -With a numeric prefix arg switch to numbered eshell buffer, if no -prefix arg provided and more than one eshell buffer exists, provide -completions on those buffers. If only one eshell buffer exists, -switch to this one, if no eshell buffer exists or if the numeric -prefix arg eshell buffer doesn't exists, create it and switch to it." - (let ((cd-eshell (lambda () - (eshell/cd helm-ff-default-directory) - (eshell-reset))) - (bufs (cl-loop for b in (mapcar 'buffer-name (buffer-list)) - when (helm-ff--eshell-interactive-buffer-p b) - collect b))) - (helm-aif (and (null helm-current-prefix-arg) - (if (cdr bufs) - (helm-comp-read "Switch to eshell buffer: " bufs - :must-match t) - (car bufs))) - (switch-to-buffer it) - (eshell helm-current-prefix-arg)) - (unless (get-buffer-process (current-buffer)) - (funcall cd-eshell)))) - -(defun helm-ff--eshell-interactive-buffer-p (buffer) - (with-current-buffer buffer - (and (eq major-mode 'eshell-mode) - (save-excursion - (goto-char (point-min)) - (eshell-next-prompt 1) - (null (eql (point) (point-min))))))) - -(defun helm-ff-touch-files (_candidate) - "The touch files action for helm-find-files." - (let* ((files (helm-marked-candidates)) - (split (cl-loop for f in files - for spt = (unless helm-current-prefix-arg - (cons (helm-basedir f) - (split-string f ", ?"))) - if spt - append (cl-loop with dir = (car spt) - for ff in (cdr spt) - collect (expand-file-name ff dir)) - else collect f)) - (timestamp (helm-comp-read - "Timestamp (default Now): " - (cl-loop for f in split - for time = (file-attributes f) - for date = (and time - (format-time-string - "%Y-%m-%d %H:%M:%S" - (nth 5 time))) - when date - collect (cons (format "%s: %s" - (helm-basename f) date) - date)) - :default - (format-time-string "%Y-%m-%d %H:%M:%S" - (current-time)))) - (failures - (cl-loop with default-directory = helm-ff-default-directory - for f in split - for file = (or (file-remote-p f 'localname) f) - when (> (process-file - "touch" nil nil nil "-d" timestamp file) - 0) - collect f))) - (when failures - (message "Failed to touch *%s files:\n%s" - (length failures) - (mapconcat (lambda (f) (format "- %s\n" f)) failures ""))))) - -(defun helm-ff-run-touch-files () - "Used to interactively run touch file action from keyboard." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-ff-touch-files))) -(put 'helm-ff-run-touch-files 'helm-only t) - -(defun helm-ff-sort-by-size () - (interactive) - (unless (eq helm-ff-initial-sort-method 'size) - (setq helm-ff-initial-sort-method 'size) - (helm-update (helm-get-selection nil helm-ff-transformer-show-only-basename))) - (message "Sorting by size")) -(put 'helm-ff-sort-by-size 'helm-only t) - -(defun helm-ff-sort-by-newest () - (interactive) - (unless (eq helm-ff-initial-sort-method 'newest) - (setq helm-ff-initial-sort-method 'newest) - (helm-update (helm-get-selection nil helm-ff-transformer-show-only-basename))) - (message "Sorting by newest")) -(put 'helm-ff-sort-by-newest 'helm-only t) - -(defun helm-ff-sort-alpha () - (interactive) - (unless (eq helm-ff-initial-sort-method nil) - (setq helm-ff-initial-sort-method nil) - (helm-update (helm-get-selection nil helm-ff-transformer-show-only-basename))) - (message "Sorting alphabetically")) -(put 'helm-ff-sort-alpha 'helm-only t) - -(defun helm-ff-serial-rename-action (method) - "Rename all marked files in `helm-ff-default-directory' with METHOD. -See `helm-ff-serial-rename-1'." - (let* ((helm--reading-passwd-or-string t) - (cands (helm-marked-candidates :with-wildcard t)) - (def-name (car cands)) - (name (helm-read-string "NewName: " - (replace-regexp-in-string - "[0-9]+$" "" - (helm-basename - def-name - (file-name-extension def-name))))) - (start (read-number "StartAtNumber: ")) - (extension (helm-read-string "Extension: " - (file-name-extension (car cands)))) - (dir (expand-file-name - (helm-read-file-name - "Serial Rename to directory: " - :initial-input - (expand-file-name helm-ff-default-directory) - :test 'file-directory-p - :must-match t))) - done) - (with-helm-display-marked-candidates - helm-marked-buffer-name (helm-ff--count-and-collect-dups cands) - (if (y-or-n-p - (format "Rename %s file(s) to <%s> like this ?\n%s " - (length cands) dir (format "%s <-> %s%s.%s" - (helm-basename (car cands)) - name start extension))) - (progn - (helm-ff-serial-rename-1 - dir cands name start extension :method method) - (setq done t) - (message nil)))) - (if done - (with-helm-current-buffer (helm-find-files-1 dir)) - (message "Operation aborted")))) - -(defun helm-ff-member-directory-p (file directory) - (let ((dir-file (expand-file-name - (file-name-as-directory (file-name-directory file)))) - (cur-dir (expand-file-name (file-name-as-directory directory)))) - (string= dir-file cur-dir))) - -(cl-defun helm-ff-serial-rename-1 - (directory collection new-name start-at-num extension &key (method 'rename)) - "rename files in COLLECTION to DIRECTORY with the prefix name NEW-NAME. -Rename start at number START-AT-NUM - ex: prefixname-01.jpg. -EXTENSION is the file extension to use, in empty prompt, -reuse the original extension of file. -METHOD can be one of rename, copy or symlink. -Files will be renamed if they are files of current directory, otherwise they -will be treated with METHOD. -Default METHOD is rename." - ;; Maybe remove directories selected by error in collection. - (setq collection (cl-remove-if 'file-directory-p collection)) - (let* ((tmp-dir (file-name-as-directory - (concat (file-name-as-directory directory) - (symbol-name (cl-gensym "tmp"))))) - (fn (cl-case method - (copy 'copy-file) - (symlink 'make-symbolic-link) - (rename 'rename-file) - (t (error "Error: Unknown method %s" method))))) - (make-directory tmp-dir) - (unwind-protect - (progn - ;; Rename all files to tmp-dir with new-name. - ;; If files are not from start directory, use method - ;; to move files to tmp-dir. - (cl-loop for i in collection - for count from start-at-num - for fnum = (if (< count 10) "0%s" "%s") - for nname = (concat tmp-dir new-name (format fnum count) - (if (not (string= extension "")) - (format ".%s" (replace-regexp-in-string - "[.]" "" extension)) - (file-name-extension i 'dot))) - do (if (helm-ff-member-directory-p i directory) - (rename-file i nname) - (funcall fn i nname))) - ;; Now move all from tmp-dir to destination. - (cl-loop with dirlist = (directory-files - tmp-dir t directory-files-no-dot-files-regexp) - for f in dirlist do - (if (file-symlink-p f) - (make-symbolic-link (file-truename f) - (concat (file-name-as-directory directory) - (helm-basename f))) - (rename-file f directory)))) - (delete-directory tmp-dir t)))) - -(defun helm-ff-serial-rename (_candidate) - "Serial rename all marked files to `helm-ff-default-directory'. -Rename only file of current directory, and symlink files coming from -other directories. -See `helm-ff-serial-rename-1'." - (helm-ff-serial-rename-action 'rename)) - -(defun helm-ff-serial-rename-by-symlink (_candidate) - "Serial rename all marked files to `helm-ff-default-directory'. -Rename only file of current directory, and symlink files coming from -other directories. -See `helm-ff-serial-rename-1'." - (helm-ff-serial-rename-action 'symlink)) - -(defun helm-ff-serial-rename-by-copying (_candidate) - "Serial rename all marked files to `helm-ff-default-directory'. -Rename only file of current directory, and copy files coming from -other directories. -See `helm-ff-serial-rename-1'." - (helm-ff-serial-rename-action 'copy)) - -(defvar helm-ff-query-replace-fnames-history-from nil) -(defvar helm-ff-query-replace-fnames-history-to nil) -(defun helm-ff-query-replace-on-filenames (candidates) - "Query replace on filenames of CANDIDATES. -This doesn't replace inside the files, only modify filenames." - (with-helm-display-marked-candidates - helm-marked-buffer-name - (mapcar 'helm-basename candidates) - (let* ((regexp (read-string "Replace regexp on filename(s): " - nil 'helm-ff-query-replace-history-from - (helm-basename (car candidates)))) - (rep (read-string (format "Replace regexp `%s' with: " regexp) - nil 'helm-ff-query-replace-history-to)) - subexp) - (cl-loop with query = "y" - with count = 0 - with target = nil - for old in candidates - for new = (concat (helm-basedir old) - (helm--replace-regexp-in-buffer-string - (save-match-data - (cond ((string= regexp "%.") - (setq subexp 1) - (helm-ff--prepare-str-with-regexp - (setq target (helm-basename old t)))) - ((string= regexp ".%") - (setq subexp 1) - (helm-ff--prepare-str-with-regexp - (setq target (file-name-extension old)))) - ((string= regexp "%") - (regexp-quote - (setq target (helm-basename old)))) - ((string-match "%:\\([0-9]+\\):\\([0-9]+\\)" regexp) - (setq subexp 1) - (let ((beg (match-string 1 regexp)) - (end (match-string 2 regexp)) - (str (helm-basename old))) - (setq target (substring str - (string-to-number beg) - (string-to-number end))) - (helm-ff--prepare-str-with-regexp str beg end))) - (t regexp))) - (save-match-data - (cond (;; Handle incremental - ;; replacement with \# in - ;; search and replace - ;; feature in placeholder \@. - (string-match - "\\\\@/\\(.*\\)/\\(\\(?99:.*\\)\\\\#\\)/" - rep) - (replace-regexp-in-string - (match-string 1 rep) - (concat (match-string 99 rep) - (format "%03d" (1+ count))) - target)) - ;; Incremental replacement - ;; before or after \@. - ((and (string-match-p "\\\\#" rep) - (string-match "\\\\@" rep)) - (replace-regexp-in-string - "\\\\#" (format "%03d" (1+ count)) - (replace-match target t t rep))) - ;; Simple incremental replacement. - ((string-match "\\\\#" rep) - (replace-match - (format "%03d" (1+ count)) t t rep)) - ;; Substring replacement in placeholder. - ((string-match - "\\\\@:\\([0-9]*\\):\\([0-9]*\\)" rep) - (replace-match (substring - target - (string-to-number - (match-string 1 rep)) - (pcase (match-string 2 rep) - ((pred (string= "")) - (length target)) - (res (string-to-number res)))) - t t rep)) - ;; Search and replace in - ;; placeholder. Doesn't - ;; handle incremental here. - ((string-match "\\\\@/\\(.*\\)/\\(.*\\)/" rep) - (replace-match (replace-regexp-in-string - (match-string 1 rep) - (match-string 2 rep) - target t) - t t rep)) - ;; Simple replacement by placeholder. - ((string-match "\\\\@" rep) - (replace-match target t t rep)) - ;; Replacement with - ;; upcase, downcase or - ;; capitalized text. - ((string= rep "%u") #'upcase) - ((string= rep "%d") #'downcase) - ((string= rep "%c") #'capitalize) - ;; Simple replacement with - ;; whole replacement regexp. - (t rep))) - (helm-basename old) t nil subexp)) - ;; If `regexp' is not matched in `old' - ;; `replace-regexp-in-string' will - ;; return `old' unmodified. - unless (string= old new) - do (progn - (when (file-exists-p new) - (setq new (concat (file-name-sans-extension new) - (format "(%s)" count) - (file-name-extension new t)))) - (unless (string= query "!") - (setq query (helm-read-answer (format - "Replace `%s' by `%s' [!,y,n,q]" - (helm-basename old) - (helm-basename new)) - '("y" "n" "!" "q")))) - (when (string= query "q") - (cl-return (message "Operation aborted"))) - (unless (string= query "n") - (rename-file old new) - (cl-incf count))) - finally (message "%d Files renamed" count)))) - ;; This fix the emacs bug where "Emacs-Lisp:" is sent - ;; in minibuffer (not the echo area). - (sit-for 0.1) - (with-current-buffer (window-buffer (minibuffer-window)) - (delete-minibuffer-contents))) - -(defun helm-ff--prepare-str-with-regexp (str &optional rep1 rep2) - ;; This is used in `helm-ff-query-replace-on-filenames' to prepare - ;; STR when REGEXP is specified as substring e.g %:1:3 in this case - ;; substring from 1 to 3 in STR will be enclosed with parenthesis to - ;; match this substring as a subexp e.g %:1:3 on string "emacs" will - ;; be replaced by "e\\(ma\\)cs" using subexp 1 like this: - ;; (helm--replace-regexp-in-buffer-string "e\\(ma\\)cs" "fo" "emacs" nil t 1) - ;; => "efocs" - ;; ^^ - ;; Where "1" and "3" will be strings extracted with match-string - ;; from regexp and refered respectively in this function as REP1 and - ;; REP2. - (let* ((from (or (and rep1 (string-to-number rep1)) 0)) - (to (or (and rep2 (string-to-number rep2)) (length str))) - (subexp (concat "\\(" (regexp-quote (substring str from to)) "\\)")) - (before-str (unless (zerop from) - (regexp-quote (substring str 0 from)))) - (after-str (unless (= to (length str)) - (regexp-quote (substring str to (length str)))))) - (concat before-str subexp after-str))) - -;; The action. -(defun helm-ff-query-replace-fnames-on-marked (_candidate) - (let ((marked (helm-marked-candidates :with-wildcard t))) - (helm-ff-query-replace-on-filenames marked))) - -;; The command for `helm-find-files-map'. -(defun helm-ff-run-query-replace-fnames-on-marked () - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-ff-query-replace-fnames-on-marked))) -(put 'helm-ff-run-query-replace-fnames-on-marked 'helm-only t) - -(defun helm-ff-query-replace (_candidate) - (let ((bufs (cl-loop for f in (helm-marked-candidates :with-wildcard t) - collect (buffer-name (find-file-noselect f))))) - (helm-buffer-query-replace-1 nil bufs))) - -(defun helm-ff-query-replace-regexp (_candidate) - (let ((bufs (cl-loop for f in (helm-marked-candidates :with-wildcard t) - collect (buffer-name (find-file-noselect f))))) - (helm-buffer-query-replace-1 'regexp bufs))) - -(defun helm-ff-run-query-replace () - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-ff-query-replace))) -(put 'helm-ff-run-query-replace 'helm-only t) - -(defun helm-ff-run-query-replace-regexp () - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-ff-query-replace-regexp))) -(put 'helm-ff-run-query-replace-regexp 'helm-only t) - -(defun helm-ff-toggle-auto-update (_candidate) - (if helm-ff--deleting-char-backward - (progn - (message "[Auto expansion disabled]") - (sit-for 1) (message nil) - (setq helm-ff--auto-update-state nil)) - (setq helm-ff-auto-update-flag (not helm-ff-auto-update-flag)) - (setq helm-ff--auto-update-state helm-ff-auto-update-flag) - (message "[Auto expansion %s]" - (if helm-ff-auto-update-flag "enabled" "disabled")))) - -(defun helm-ff-run-toggle-auto-update () - (interactive) - (with-helm-alive-p - (helm-attrset 'toggle-auto-update '(helm-ff-toggle-auto-update . never-split)) - (helm-execute-persistent-action 'toggle-auto-update))) -(put 'helm-ff-run-toggle-auto-update 'helm-only t) - -(defun helm-ff-delete-char-backward () - "Go up one level or disable HFF auto update and delete char backward. - -Going up one level works only when pattern is a directory endings with -\"/\", otherwise this command delete char backward. - -Going up one level can be disabled if necessary by deleting \"/\" at -end of pattern using \\\\[backward-char] and \\[helm-delete-minibuffer-contents]." - (interactive) - (with-helm-alive-p - (if (and helm-ff-DEL-up-one-level-maybe - (string-match "/\\'" helm-pattern) - (file-directory-p helm-pattern)) - (call-interactively 'helm-find-files-up-one-level) - (setq helm-ff-auto-update-flag nil) - (setq helm-ff--deleting-char-backward t) - (call-interactively - (lookup-key (current-global-map) - (read-kbd-macro "DEL"))) - (helm--update-header-line)))) -(put 'helm-ff-delete-char-backward 'helm-only t) - -(defun helm-ff-delete-char-backward--exit-fn () - (setq helm-ff-auto-update-flag helm-ff--auto-update-state) - (setq helm-ff--deleting-char-backward nil)) - -(defvar helm-ff--RET-disabled nil) -(defun helm-ff-RET-1 (&optional must-match) - "Used for RET action in `helm-find-files'. -See `helm-ff-RET' for details. -If MUST-MATCH is specified exit with -`helm-confirm-and-exit-minibuffer' which handle must-match mechanism." - (let ((sel (helm-get-selection))) - (cl-assert sel nil "Trying to exit with no candidates") - (if (and (file-directory-p sel) - ;; Allows exiting with default action when a prefix arg - ;; is specified. - (null current-prefix-arg) - (null helm-ff--RET-disabled) - (not (string= "." (helm-basename sel)))) - (helm-execute-persistent-action) - (if must-match - (helm-confirm-and-exit-minibuffer) - (helm-maybe-exit-minibuffer))))) - -(defun helm-ff-RET () - "Default action for RET in `helm-find-files'. - -Behave differently depending of `helm-selection': - -- candidate basename is \".\" => open it in dired. -- candidate is a directory => expand it. -- candidate is a file => open it." - (interactive) - (helm-ff-RET-1)) -(put 'helm-ff-RET 'helm-only t) - -(defun helm-ff-TAB-1 (&optional force-menu) - "Used for TAB action in `helm-find-files'." - (let ((sel (helm-get-selection))) - (if (and (null force-menu) - (file-directory-p sel) - (not (string= "." (helm-basename sel)))) - (helm-execute-persistent-action) - (helm-select-action)))) - -(defun helm-ff-TAB (arg) - "Default action for TAB in `helm-find-files'. - -Behave differently depending of `helm-selection': - -- candidate basename is \".\" => open the action menu. -- candidate is a directory => expand it. -- candidate is a file => open action menu. - -Called with a prefix arg open menu unconditionally." - (interactive "P") - (helm-ff-TAB-1 arg)) -(put 'helm-ff-TAB 'helm-only t) - -(defun helm-ff-RET-must-match () - "Same as `helm-ff-RET' but used in must-match map." - (interactive) - (helm-ff-RET-1 t)) - -(defun helm-ff-run-grep () - "Run Grep action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-find-files-grep))) -(put 'helm-ff-run-grep 'helm-only t) - -(defun helm-ff-run-git-grep () - "Run git-grep action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-ff-git-grep))) -(put 'helm-ff-run-git-grep 'helm-only t) - -(defun helm-ff-run-grep-ag () - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-find-files-ag))) -(put 'helm-ff-run-grep-ag 'helm-only t) - -(defun helm-ff-run-pdfgrep () - "Run Pdfgrep action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-ff-pdfgrep))) -(put 'helm-ff-run-pdfgrep 'helm-only t) - -(defun helm-ff-run-zgrep () - "Run Grep action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-ff-zgrep))) -(put 'helm-ff-run-zgrep 'helm-only t) - -(defun helm-ff-run-copy-file () - "Run Copy file action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-find-files-copy))) -(put 'helm-ff-run-copy-file 'helm-only t) - -(defun helm-ff-run-rename-file () - "Run Rename file action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-find-files-rename))) -(put 'helm-ff-run-rename-file 'helm-only t) - -(defun helm-ff-run-byte-compile-file () - "Run Byte compile file action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-find-files-byte-compile))) -(put 'helm-ff-run-byte-compile-file 'helm-only t) - -(defun helm-ff-run-load-file () - "Run Load file action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-find-files-load-files))) -(put 'helm-ff-run-load-file 'helm-only t) - -(defun helm-ff-run-eshell-command-on-file () - "Run eshell command on file action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action - 'helm-find-files-eshell-command-on-file))) -(put 'helm-ff-run-eshell-command-on-file 'helm-only t) - -(defun helm-ff-run-ediff-file () - "Run Ediff file action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-find-files-ediff-files))) -(put 'helm-ff-run-ediff-file 'helm-only t) - -(defun helm-ff-run-ediff-merge-file () - "Run Ediff merge file action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action - 'helm-find-files-ediff-merge-files))) -(put 'helm-ff-run-ediff-merge-file 'helm-only t) - -(defun helm-ff-run-symlink-file () - "Run Symlink file action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-find-files-symlink))) -(put 'helm-ff-run-symlink-file 'helm-only t) - -(defun helm-ff-run-relsymlink-file () - "Run Symlink file action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-find-files-relsymlink))) -(put 'helm-ff-run-relsymlink-file 'helm-only t) - -(defun helm-ff-run-hardlink-file () - "Run Hardlink file action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-find-files-hardlink))) -(put 'helm-ff-run-hardlink-file 'helm-only t) - -(defun helm-ff-delete-files (candidate) - "Delete files default action." - (funcall helm-ff-delete-files-function candidate)) - -(defun helm-ff-run-delete-file () - "Run Delete file action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action #'helm-ff-delete-files))) -(put 'helm-ff-run-delete-file 'helm-only t) - -(defun helm-ff-run-complete-fn-at-point () - "Run complete file name action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action - 'helm-insert-file-name-completion-at-point))) -(put 'helm-ff-run-complete-fn-at-point 'helm-only t) - -(defun helm-ff-run-switch-to-eshell () - "Run switch to eshell action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-ff-switch-to-eshell))) -(put 'helm-ff-run-switch-to-eshell 'helm-only t) - -(defun helm-ff-run-switch-other-window () - "Run switch to other window action from `helm-source-find-files'. -When a prefix arg is provided, split is done vertically." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-find-files-other-window))) -(put 'helm-ff-run-switch-other-window 'helm-only t) - -(defun helm-ff-run-switch-other-frame () - "Run switch to other frame action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'find-file-other-frame))) -(put 'helm-ff-run-switch-other-frame 'helm-only t) - -(defun helm-ff-run-open-file-externally () - "Run open file externally command action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-open-file-externally))) -(put 'helm-ff-run-open-file-externally 'helm-only t) - -(defun helm-ff-run-open-file-with-default-tool () - "Run open file externally command action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-open-file-with-default-tool))) -(put 'helm-ff-run-open-file-with-default-tool 'helm-only t) - -(defun helm-ff-locate (candidate) - "Locate action function for `helm-find-files'." - (helm-locate-set-command) - (let ((default (concat (helm-basename - (expand-file-name - candidate - helm-ff-default-directory)) - (unless (or - ;; "-b" is already added when fuzzy matching. - helm-locate-fuzzy-match - ;; The locate '-b' option doesn't exists - ;; in everything (es). - (and (eq system-type 'windows-nt) - (string-match "^es" helm-locate-command))) - " -b")))) - (helm-locate-1 helm-current-prefix-arg nil 'from-ff default))) - -(defun helm-ff-run-locate () - "Run locate action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-ff-locate))) -(put 'helm-ff-run-locate 'helm-only t) - -(defun helm-files-insert-as-org-link (candidate) - (insert (format "[[%s][]]" candidate)) - (goto-char (- (point) 2))) - -(defun helm-ff-run-insert-org-link () - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-files-insert-as-org-link))) -(put 'helm-ff-run-insert-org-link 'helm-only t) - -(defun helm-ff-run-find-file-as-root () - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-find-file-as-root))) -(put 'helm-ff-run-find-file-as-root 'helm-only t) - -(defun helm-ff-run-find-alternate-file () - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'find-alternate-file))) -(put 'helm-ff-run-find-alternate-file 'helm-only t) - -(defun helm-ff-run-mail-attach-files () - "Run mail attach files command action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-ff-mail-attach-files))) -(put 'helm-ff-run-mail-attach-files 'helm-only t) - -(defun helm-ff-run-etags () - "Run Etags command action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-ff-etags-select))) -(put 'helm-ff-run-etags 'helm-only t) - -(defvar lpr-printer-switch) -(defun helm-ff-print (_candidate) - "Print marked files. - -You may to set in order -variables `lpr-command',`lpr-switches' and/or `printer-name', -but with no settings helm should detect your printer(s) and -print with the default `lpr' settings. - -NOTE: DO NOT set the \"-P\" flag in `lpr-switches', if you really -have to modify this, do it in `lpr-printer-switch'. - -Same as `dired-do-print' but for helm." - (require 'lpr) - (when (or helm-current-prefix-arg - (not helm-ff-printer-list)) - (setq helm-ff-printer-list - (helm-ff-find-printers))) - (let* ((file-list (helm-marked-candidates :with-wildcard t)) - (len (length file-list)) - (printer-name (if helm-ff-printer-list - (helm-comp-read - "Printer: " helm-ff-printer-list) - printer-name)) - (lpr-switches - (if (and (stringp printer-name) - (string< "" printer-name)) - (cons (concat lpr-printer-switch printer-name) - lpr-switches) - lpr-switches)) - (command (helm-read-string - (format "Print *%s File(s):\n%s with: " - len - (mapconcat - (lambda (f) (format "- %s\n" f)) - file-list "")) - (when (and lpr-command lpr-switches) - (mapconcat 'identity - (cons lpr-command - (if (stringp lpr-switches) - (list lpr-switches) - lpr-switches)) - " ")))) - (file-args (mapconcat (lambda (x) - (format "'%s'" x)) - file-list " ")) - (cmd-line (concat command " " file-args))) - (if command - (start-process-shell-command "helm-print" nil cmd-line) - (error "Error: Please verify your printer settings in Emacs.")))) - -(defun helm-ff-run-print-file () - "Run Print file action from `helm-source-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-ff-print))) -(put 'helm-ff-run-print-file 'helm-only t) - -(defun helm-ff-checksum (file) - "Calculate the checksum of FILE. -The checksum is copied to kill-ring. -Checksum is calculated with the md5sum, sha1sum, sha224sum, sha256sum, -sha384sum and sha512sum when available, otherwise the emacs function -`secure-hash' is used but it is slow and may crash Emacs and even the -whole system as it eats all memory." - (cl-assert (file-regular-p file) - nil "`%s' is not a regular file" file) - (let* ((algo (intern (helm-comp-read - "Algorithm: " - '(md5 sha1 sha224 sha256 sha384 sha512)))) - (cmd (concat (symbol-name algo) "sum")) - (bn (helm-basename file)) - proc) - (message "Calculating %s checksum for %s..." algo bn) - (if (executable-find cmd) - (progn - (set-process-filter - (setq proc (start-file-process cmd nil cmd "-b" file)) - (lambda (_process output) - (when output (kill-new output)))) - (set-process-sentinel - proc - `(lambda (_process event) - (when (string= event "finished\n") - (message "Calculating %s checksum for `%s' done and copied to kill-ring" - ,(symbol-name algo) ,bn))))) - (async-let ((sum (with-temp-buffer - (insert-file-contents-literally file) - (secure-hash algo (current-buffer))))) - (kill-new sum) - (message "Calculating %s checksum for `%s' done and copied to kill-ring" - algo bn))))) - -(defun helm-ff-toggle-basename (_candidate) - (with-helm-buffer - (setq helm-ff-transformer-show-only-basename - (not helm-ff-transformer-show-only-basename)) - (let* ((cand (helm-get-selection nil t)) - (target (if helm-ff-transformer-show-only-basename - (helm-basename cand) cand))) - (helm-force-update (concat (regexp-quote target) "$"))))) - -(defun helm-ff-run-toggle-basename () - (interactive) - (with-helm-alive-p - (unless (helm-empty-source-p) - (helm-ff-toggle-basename nil)))) -(put 'helm-ff-run-toggle-basename 'helm-only t) - -(defun helm-reduce-file-name-1 (fname level) - ;; This is the old version of helm-reduce-file-name, we still use it - ;; with ftp fnames as expand-file-name is not working as expected - ;; with ftp fnames (emacs bug). - (cl-loop with result - with iter = (helm-iter-reduce-fname (expand-file-name fname)) - repeat level do (setq result (helm-iter-next iter)) - finally return (or result (expand-file-name "/")))) - -(defun helm-reduce-file-name-2 (fname level) - ;; This version comes from issue #2004 (UNC paths) and should fix - ;; it. It works with local files and remote files as well but not - ;; with ftp, see helm-reduce-file-name-1. - (while (> level 0) - (unless (or (string= fname "/") - (string= (file-remote-p fname 'localname) "/")) - (setq fname (expand-file-name - (concat (expand-file-name fname) "/../")))) - (setq level (1- level))) - fname) - -(defun helm-reduce-file-name (fname level) - "Reduce FNAME by number LEVEL from end." - (if (helm-aand (file-remote-p fname 'method) - (string= it "ftp")) - (helm-reduce-file-name-1 fname level) - (helm-reduce-file-name-2 fname level))) - -(defun helm-iter-reduce-fname (fname) - "Yield FNAME reduced by one level at each call." - (let ((split (split-string fname "/" t))) - (unless (or (null split) - (string-match "\\`\\(~\\|[[:alpha:]]:\\)" (car split))) - (setq split (cons "/" split))) - (lambda () - (when (and split (cdr split)) - (cl-loop for i in (setq split (butlast split)) - concat (if (string= i "/") i (concat i "/"))))))) - -(defvar helm-find-files--level-tree nil) -(defvar helm-find-files--level-tree-iterator nil) -(defun helm-find-files-up-one-level (arg) - "Go up one level like unix command `cd ..'. -If prefix numeric arg is given go ARG level up." - (interactive "p") - (with-helm-alive-p - (let ((src (helm-get-current-source))) - (when (and (helm-file-completion-source-p src) - (not (helm-ff--invalid-tramp-name-p))) - (with-helm-window - (when (helm-follow-mode-p) - (helm-follow-mode -1) (message nil))) - ;; When going up one level we want to be at the line - ;; corresponding to actual directory, so store this info - ;; in `helm-ff-last-expanded'. - (let ((cur-cand (helm-get-selection nil nil src)) - (new-pattern (helm-reduce-file-name helm-pattern arg))) - ;; Ensure visibility on all candidates for preselection. - (helm-attrset 'candidate-number-limit - (if helm-ff-up-one-level-preselect - (max (gethash new-pattern - helm-ff--directory-files-hash - helm-ff-candidate-number-limit) - helm-ff-candidate-number-limit) - helm-ff-candidate-number-limit)) - (cond ((file-directory-p helm-pattern) - (setq helm-ff-last-expanded helm-ff-default-directory)) - ((file-exists-p helm-pattern) - (setq helm-ff-last-expanded helm-pattern)) - ((and cur-cand (file-exists-p cur-cand)) - (setq helm-ff-last-expanded cur-cand))) - (unless helm-find-files--level-tree - (setq helm-find-files--level-tree - (cons helm-ff-default-directory - helm-find-files--level-tree))) - (setq helm-find-files--level-tree-iterator nil) - (push new-pattern helm-find-files--level-tree) - (helm-set-pattern new-pattern helm-suspend-update-flag) - (with-helm-after-update-hook (helm-ff-retrieve-last-expanded))))))) -(put 'helm-find-files-up-one-level 'helm-only t) - -(defun helm-find-files-down-last-level () - "Retrieve previous paths reached by `C-l' in helm-find-files." - (interactive) - (with-helm-alive-p - (when (and (helm-file-completion-source-p) - (not (helm-ff--invalid-tramp-name-p))) - (unless helm-find-files--level-tree-iterator - (setq helm-find-files--level-tree-iterator - (helm-iter-list (cdr helm-find-files--level-tree)))) - (setq helm-find-files--level-tree nil) - (helm-aif (helm-iter-next helm-find-files--level-tree-iterator) - (helm-set-pattern it) - (setq helm-find-files--level-tree-iterator nil))))) -(put 'helm-find-files-down-last-level 'helm-only t) - -(defun helm-find-files--reset-level-tree () - (setq helm-find-files--level-tree-iterator nil - helm-find-files--level-tree nil)) - -(add-hook 'helm-cleanup-hook 'helm-find-files--reset-level-tree) -(add-hook 'post-self-insert-hook 'helm-find-files--reset-level-tree) -(add-hook 'helm-after-persistent-action-hook 'helm-find-files--reset-level-tree) - -(defun helm-ff-retrieve-last-expanded () - "Move overlay to last visited directory `helm-ff-last-expanded'. -This happen after using `helm-find-files-up-one-level', -or hitting C-j on \"..\"." - (when helm-ff-last-expanded - (let ((presel (if helm-ff-transformer-show-only-basename - (helm-basename - (directory-file-name helm-ff-last-expanded)) - (directory-file-name helm-ff-last-expanded)))) - (with-helm-window - (when (re-search-forward (concat "^" (regexp-quote presel) "$") nil t) - (forward-line 0) - (helm-mark-current-line))) - (setq helm-ff-last-expanded nil)))) - -(defun helm-ff-move-to-first-real-candidate () - "When candidate is an incomplete file name move to first real candidate." - (let* ((src (helm-get-current-source)) - (name (assoc-default 'name src)) - ;; Ensure `helm-file-completion-source-p' returns nil on - ;; `helm-read-file-name' history. - minibuffer-completing-file-name) - (helm-aif (and (helm-file-completion-source-p src) - (not (helm-empty-source-p)) - ;; Prevent dired commands moving to first real - ;; (Issue #910). - (or (memq (intern-soft name) - helm-ff-goto-first-real-dired-exceptions) - (not (string-match "\\`[Dd]ired-" name))) - helm-ff--move-to-first-real-candidate - (helm-get-selection nil nil src)) - (unless (or (not (stringp it)) - (and (string-match helm-tramp-file-name-regexp it) - (not (file-remote-p it nil t))) - (file-exists-p it)) - (helm-next-line))))) - -;;; Auto-update - helm-find-files auto expansion of directories. -;; -;; -(defun helm-ff-update-when-only-one-matched () - "Expand to directory when sole completion. -When only one candidate is remaining and it is a directory, -expand to this directory. -This happen only when `helm-ff-auto-update-flag' is non--nil -or when `helm-pattern' is equal to \"~/\"." - (let ((src (helm-get-current-source))) - (when (and (helm-file-completion-source-p src) - (not (get-buffer-window helm-action-buffer 'visible)) - (not (helm-ff--invalid-tramp-name-p)) - (not (string-match-p "\\`[.]\\{2\\}[^/]+" - (helm-basename helm-pattern)))) - (with-helm-buffer - (let* ((history-p (string= (assoc-default 'name src) - "Read File Name History")) - (pat (if (string-match helm-tramp-file-name-regexp - helm-pattern) - (helm-ff--create-tramp-name helm-pattern) - helm-pattern)) - (completed-p (string= (file-name-as-directory - (expand-file-name - (substitute-in-file-name pat))) - helm-ff-default-directory)) - (candnum (helm-get-candidate-number)) - (lt2-p (and (<= candnum 2) - (>= (string-width (helm-basename helm-pattern)) 2))) - (cur-cand (prog2 - (unless (or completed-p - (file-exists-p pat) - history-p (null lt2-p)) - ;; Only one non--existing candidate - ;; and one directory candidate, move to it, - ;; but not when renaming, copying etc..., - ;; so for this use - ;; `helm-ff-move-to-first-real-candidate' - ;; instead of `helm-next-line' (Issue #910). - (helm-ff-move-to-first-real-candidate)) - (helm-get-selection nil nil src)))) - (when (and (or (and helm-ff-auto-update-flag - (null helm-ff--deleting-char-backward) - ;; Issue #295 - ;; File predicates are returning t - ;; with paths like //home/foo. - ;; So check it is not the case by regexp - ;; to allow user to do C-a / to start e.g - ;; entering a tramp method e.g /sudo::. - (not (string-match "\\`//" helm-pattern)) - (not (eq last-command 'helm-yank-text-at-point))) - ;; Fix issue #542. - (string= helm-pattern "~/") - ;; Only one remaining directory, expand it. - (and (= candnum 1) - helm-ff--auto-update-state - (file-accessible-directory-p pat) - (null helm-ff--deleting-char-backward))) - (or - ;; Only one candidate remaining - ;; and at least 2 char in basename. - lt2-p - ;; Already completed. - completed-p) - (not history-p) ; Don't try to auto complete in history. - (stringp cur-cand) - (file-accessible-directory-p cur-cand)) - (if (and (not (helm-dir-is-dot cur-cand)) ; [1] - ;; Maybe we are here because completed-p is true - ;; but check this again to be sure. (Windows fix) - (<= candnum 2)) ; [2] - ;; If after going to next line the candidate - ;; is not one of "." or ".." [1] - ;; and only one candidate is remaining [2], - ;; assume candidate is a new directory to expand, and do it. - (helm-set-pattern (file-name-as-directory cur-cand)) - ;; The candidate is one of "." or ".." - ;; that mean we have entered the last letter of the directory name - ;; in prompt, so expansion is already done, just add the "/" at end - ;; of name unless helm-pattern ends with "." - ;; (i.e we are writing something starting with ".") - (unless (string-match "\\`.*[.]\\{1\\}\\'" helm-pattern) - (helm-set-pattern - ;; Need to expand-file-name to avoid e.g /ssh:host:./ in prompt. - (expand-file-name (file-name-as-directory helm-pattern))))) - (helm-check-minibuffer-input))))))) - -(defun helm-ff-auto-expand-to-home-or-root () - "Allow expanding to home/user directory or root or text yanked after pattern." - (when (and (helm-file-completion-source-p) - (with-current-buffer (window-buffer (minibuffer-window)) (eolp)) - (not (string-match helm-ff-url-regexp helm-pattern))) - (cond ((and (not (file-remote-p helm-pattern)) - (null (file-exists-p helm-pattern)) - (string-match-p - "\\`\\([.]\\|\\s-\\)\\{2\\}[^/]+" - (helm-basename helm-pattern)) - (string-match-p "/\\'" helm-pattern)) - (helm-ff-recursive-dirs helm-pattern) - (with-helm-window (helm-check-minibuffer-input))) - ((string-match - "\\(?:\\`~/\\)\\|/?\\$.*/\\|/\\./\\|/\\.\\./\\|/~.*/\\|//\\|\\(/[[:alpha:]]:/\\|\\s\\+\\)" - helm-pattern) - (let* ((match (match-string 0 helm-pattern)) - (input (cond ((string= match "/./") - (expand-file-name default-directory)) - ((string= helm-pattern "/../") "/") - ((string-match-p "\\`/\\$" match) - (let ((sub (substitute-in-file-name match))) - (if (file-directory-p sub) - sub (replace-regexp-in-string "/\\'" "" sub)))) - (t (helm-ff--expand-substitued-pattern helm-pattern))))) - ;; `file-directory-p' returns t on "/home/me/." (issue #1844). - (if (and (file-directory-p input) - (not (string-match-p "[^.]\\.\\'" input))) - (setq helm-ff-default-directory - (setq input (file-name-as-directory input))) - (setq helm-ff-default-directory (file-name-as-directory - (file-name-directory input)))) - (with-helm-window - (helm-set-pattern input) - (helm-check-minibuffer-input))))))) - -(defun helm-ff--expand-file-name-no-dot (name &optional directory) - "Prevent expanding \"/home/user/.\" to \"/home/user\"." - ;; Issue #1844 - If user enter "~/." to type an hidden filename - ;; don't expand to /home/him e.g. - ;; (expand-file-name "~/.") =>"/home/thierry" - ;; (helm-ff--expand-substitued-pattern "~/.") =>"/home/thierry/." - (concat (expand-file-name name directory) - (and (string-match "[^.]\\.\\'" name) "/."))) - -(defun helm-ff--expand-substitued-pattern (pattern) - ;; [Windows] On UNC paths "/" expand to current machine, - ;; so use the root of current Drive. (i.e "C:/") - (let* ((directory (and (memq system-type '(windows-nt ms-dos)) - (getenv "SystemDrive"))) - ;; On Windows use a simple call to `expand-file-name' to - ;; avoid Issue #2004. - (expand-fn (if directory - #'expand-file-name - #'helm-ff--expand-file-name-no-dot))) - (funcall expand-fn (helm-substitute-in-filename pattern) - ;; directory is nil on Nix. - directory))) - -(defun helm-substitute-in-filename (fname) - "Substitute all parts of FNAME from start up to \"~/\" or \"/\". -On windows system substitute from start up to \"/[[:lower:]]:/\". -This function is needed for `helm-ff-auto-expand-to-home-or-root' -and should be used carefully elsewhere, or not at all, using -`substitute-in-file-name' instead." - (cond ((and helm--url-regexp - (string-match-p helm--url-regexp fname)) - fname) - ((and (file-remote-p fname) - helm-substitute-in-filename-stay-on-remote) - (let ((sub (substitute-in-file-name fname))) - (if (file-directory-p sub) - sub (replace-regexp-in-string "/\\'" "" sub)))) - (t - (with-temp-buffer - (insert fname) - (goto-char (point-min)) - (when (memq system-type '(windows-nt ms-dos)) - (skip-chars-forward "/")) ;; Avoid infloop in UNC paths Issue #424 - (if (re-search-forward "~.*/?\\|//\\|/[[:alpha:]]:/" nil t) - (let ((match (match-string 0))) - (goto-char (if (or (string= match "//") - (string-match-p "/[[:alpha:]]:/" match)) - (1+ (match-beginning 0)) - (match-beginning 0))) - (buffer-substring-no-properties (point) (point-at-eol))) - fname))))) - -(defun helm-point-file-in-dired (file) - "Put point on filename FILE in dired buffer." - (unless (and helm--url-regexp - (string-match-p helm--url-regexp file)) - (let ((target (expand-file-name (helm-substitute-in-filename file)))) - (dired (file-name-directory target)) - (dired-goto-file target)))) - -(defun helm-marked-files-in-dired (_candidate) - "Open a dired buffer with only marked files. - -With a prefix arg toggle dired buffer to wdired mode." - (advice-add 'wdired-finish-edit :override #'helm--advice-wdired-finish-edit) - (advice-add 'wdired-get-filename :override #'helm--advice-wdired-get-filename) - (let* ((marked (helm-marked-candidates :with-wildcard t)) - (current (car marked))) - (unless (and helm--url-regexp - (string-match-p helm--url-regexp current)) - (let ((target (expand-file-name (helm-substitute-in-filename current)))) - (dired (cons helm-ff-default-directory marked)) - (dired-goto-file target) - (when (or helm-current-prefix-arg current-prefix-arg) - (call-interactively 'wdired-change-to-wdired-mode)))))) - -(defun helm-ff-run-marked-files-in-dired () - "Execute `helm-marked-files-in-dired' interactively." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-marked-files-in-dired))) -(put 'helm-ff-run-marked-files-in-dired 'helm-only t) - -(defun helm-ff--create-tramp-name (fname) - "Build filename from `helm-pattern' like /su:: or /sudo::." - ;; `tramp-make-tramp-file-name' takes 7 args on emacs-26 whereas it - ;; takes only 5 args in emacs-24/25. - (apply #'tramp-make-tramp-file-name - ;; `tramp-dissect-file-name' returns a list in emacs-26 - ;; whereas in 24.5 it returns a vector, thus the car is a - ;; symbol (`tramp-file-name') which is not needed as argument - ;; for `tramp-make-tramp-file-name' so transform the cdr in - ;; vector, and for 24.5 use directly the returned value. - (cl-loop with v = (helm-ff--tramp-cons-or-vector - (tramp-dissect-file-name fname)) - for i across v collect i))) - -(defun helm-ff--tramp-cons-or-vector (vector-or-cons) - "Return VECTOR-OR-CONS as a vector." - (pcase vector-or-cons - (`(,_l . ,ll) (vconcat ll)) - ((and vec (pred vectorp)) vec))) - -(defun helm-ff--get-tramp-methods () - "Returns a list of the car of `tramp-methods'." - (or helm-ff--tramp-methods - (setq helm-ff--tramp-methods (mapcar 'car tramp-methods)))) - -(defun helm-ff--previous-mh-tramp-method (str) - (save-match-data - (with-temp-buffer - (insert str) - (when (re-search-backward - (concat "\\([|]\\)\\(" - (mapconcat 'identity (helm-ff--get-tramp-methods) "\\|") - "\\):") - nil t) - (list - (buffer-substring-no-properties (point-at-bol) (match-beginning 2)) - (buffer-substring-no-properties (match-beginning 2) (match-end 2))))))) - -(defun helm-ff--get-host-from-tramp-invalid-fname (fname) - "Extract hostname from an incomplete tramp file name. -Return nil on valid file name remote or not." - ;; Check first if whole file is remote (file-remote-p is inefficient - ;; in this case) otherwise we are matching e.g. /home/you/ssh:foo/ - ;; which is not a remote name. - ;; FIXME this will not work with a directory or a file named like - ;; "ssh:foo" and located at root (/) but it seems there is no real - ;; solution apart disabling tramp-mode when a file/dir located at / - ;; is matching helm-tramp-file-name-regexp; This would prevent usage - ;; of tramp if one have such a directory at / (who would want to - ;; have such a dir at / ???) See emacs-bug#31489. - (when (string-match-p helm-tramp-file-name-regexp fname) - (let* ((bn (helm-basename fname)) - (bd (replace-regexp-in-string (regexp-quote bn) "" fname)) - (split (split-string bn ":" t)) - (meth (car (member (car split) - (helm-ff--get-tramp-methods))))) - (and meth (string= bd "/") (car (last split)))))) - -(cl-defun helm-ff--tramp-hostnames (&optional (pattern helm-pattern)) - "Get a list of hosts for tramp method found in `helm-pattern'. -Argument PATTERN default to `helm-pattern', it is here only for debugging -purpose." - (when (string-match helm-tramp-file-name-regexp pattern) - (let* ((mh-method (helm-ff--previous-mh-tramp-method pattern)) - (method (or (cadr mh-method) (match-string 1 pattern))) - (current-mh-host (helm-aif (and mh-method - (helm-ff--get-host-from-tramp-invalid-fname pattern)) - (concat (car mh-method) method ":" - (car (split-string it "|" t))))) - (all-methods (helm-ff--get-tramp-methods)) - (comps (cl-loop for (f . h) in (tramp-get-completion-function method) - append (cl-loop for e in (funcall f (car h)) - for host = (and (consp e) (cadr e)) - when (and host (not (member host all-methods))) - collect (concat (or (car mh-method) "/") - method ":" host))))) - (helm-fast-remove-dups - (delq nil (cons current-mh-host comps)) - :test 'equal)))) - -(defun helm-ff-before-action-hook-fn () - "Exit helm when user try to execute action on an invalid tramp fname." - (let* ((src (helm-get-current-source)) - (cand (helm-get-selection nil nil src))) - (when (and (helm-file-completion-source-p src) - (stringp cand) - (helm-ff--invalid-tramp-name-p cand) ; Check candidate. - (helm-ff--invalid-tramp-name-p)) ; check helm-pattern. - (error "Error: Unknown file or directory `%s'" cand)))) -(add-hook 'helm-before-action-hook 'helm-ff-before-action-hook-fn) - -(cl-defun helm-ff--invalid-tramp-name-p (&optional (pattern helm-pattern)) - "Return non--nil when PATTERN is an invalid tramp filename." - (string= (helm-ff-set-pattern pattern) - "Invalid tramp file name")) - -(defun helm-ff--tramp-postfixed-p (str) - (let (result) - (save-match-data - (with-temp-buffer - (save-excursion (insert str)) - (helm-awhile (search-forward ":" nil t) - (if (save-excursion - (forward-char -1) - (looking-back - (mapconcat 'identity (helm-ff--get-tramp-methods) "\\|") - (point-at-bol))) - (setq result nil) - (setq result it))))) - result)) - -(defun helm-ff-set-pattern (pattern) - "Handle tramp filenames in `helm-pattern'." - (let* ((methods (helm-ff--get-tramp-methods)) - ;; Returns the position of last ":" entered. - (postfixed (helm-ff--tramp-postfixed-p pattern)) - (reg "\\`/\\([^[/:]+\\|[^/]+]\\):.*:") - cur-method tramp-name) - ;; In some rare cases tramp can return a nil input, - ;; so be sure pattern is a string for safety (Issue #476). - (unless pattern (setq pattern "")) - (cond ((string-match helm-ff-url-regexp pattern) pattern) - ((string-match "\\`\\$" pattern) - (substitute-in-file-name pattern)) - ((string= pattern "") "") - ((string-match "\\`[.]\\{1,2\\}/\\'" pattern) - (expand-file-name pattern)) - ;; Directories ending by a dot (issue #1940) - ((string-match "[^/][.]/\\'" pattern) - (expand-file-name pattern)) - ((string-match ".*\\(~?/?[.]\\{1\\}/\\)\\'" pattern) - (expand-file-name default-directory)) - ((string-match ".*\\(~//\\|//\\)\\'" pattern) - (expand-file-name "/")) ; Expand to "/" or "c:/" - ((string-match "\\`\\(~/\\|.*/~/\\)\\'" pattern) - (expand-file-name "~/")) - ((string-match "\\`~/" pattern) - (expand-file-name pattern)) - ;; Match "/method:maybe_hostname:~" - ((and (string-match (concat reg "~") pattern) - postfixed - (setq cur-method (match-string 1 pattern)) - (member cur-method methods)) - (setq tramp-name (expand-file-name - (helm-ff--create-tramp-name - (match-string 0 pattern)))) - (replace-match tramp-name nil t pattern)) - ;; Match "/method:maybe_hostname:" - ((and (string-match reg pattern) - postfixed - (setq cur-method (match-string 1 pattern)) - (member cur-method methods)) - (setq tramp-name (helm-ff--create-tramp-name - (match-string 0 pattern))) - (replace-match tramp-name nil t pattern)) - ;; Match "/hostname:" - ((and (string-match helm-tramp-file-name-regexp pattern) - postfixed - (setq cur-method (match-string 1 pattern)) - (and cur-method (not (member cur-method methods)))) - (setq tramp-name (helm-ff--create-tramp-name - (match-string 0 pattern))) - (replace-match tramp-name nil t pattern)) - ;; Match "/method:" in this case don't try to connect. - ((and (null postfixed) - (string-match helm-tramp-file-name-regexp pattern) - (member (match-string 1 pattern) methods)) - "Invalid tramp file name") ; Write in helm-buffer. - ;; Return PATTERN unchanged. - (t pattern)))) - -(defun helm-find-files-get-candidates (&optional require-match) - "Create candidate list for `helm-source-find-files'." - (let* ((path (helm-ff-set-pattern helm-pattern)) - (dir-p (file-accessible-directory-p path)) - basedir - invalid-basedir - non-essential - (tramp-verbose helm-tramp-verbose)) ; No tramp message when 0. - ;; Tramp check if path is valid without waiting a valid - ;; connection and may send a file-error. - (setq helm--ignore-errors (file-remote-p path)) - (set-text-properties 0 (length path) nil path) - ;; Issue #118 allow creation of newdir+newfile. - (unless (or - ;; A tramp file name not completed. - (string= path "Invalid tramp file name") - ;; An empty pattern - (string= path "") - (and (string-match-p ":\\'" path) - (helm-ff--tramp-postfixed-p path)) - ;; Check if base directory of PATH is valid. - (helm-aif (file-name-directory path) - ;; If PATH is a valid directory IT=PATH, - ;; else IT=basedir of PATH. - (file-directory-p it))) - ;; BASEDIR is invalid, that's mean user is starting - ;; to write a non--existing path in minibuffer - ;; probably to create a 'new_dir' or a 'new_dir+new_file'. - (setq invalid-basedir t)) - ;; Don't set now `helm-pattern' if `path' == "Invalid tramp file name" - ;; like that the actual value (e.g /ssh:) is passed to - ;; `helm-ff--tramp-hostnames'. - (unless (or (string= path "Invalid tramp file name") - invalid-basedir) ; Leave helm-pattern unchanged. - (setq helm-ff-auto-update-flag ; [1] - ;; Unless auto update is disabled start auto updating only - ;; at third char. - (unless (or (null helm-ff--auto-update-state) - ;; But don't enable auto update when - ;; deleting backward. - helm-ff--deleting-char-backward - (and dir-p (not (string-match-p "/\\'" path)))) - (or (>= (length (helm-basename path)) 3) dir-p))) - ;; At this point the tramp connection is triggered. - (helm-log - "Pattern=%S" - (setq helm-pattern (helm-ff--transform-pattern-for-completion path))) - ;; This have to be set after [1] to allow deleting char backward. - (setq basedir (or (helm-aand - (if (and dir-p helm-ff-auto-update-flag) - ;; Add the final "/" to path - ;; when `helm-ff-auto-update-flag' is enabled. - (file-name-as-directory path) - (if (string= path "") - "/" (file-name-directory path))) - (expand-file-name it)) - default-directory)) - (setq helm-ff-default-directory - (if (string= helm-pattern "") - (expand-file-name "/") ; Expand to "/" or "c:/" - ;; If path is an url *default-directory have to be nil. - (unless (or (string-match helm-ff-url-regexp path) - (and helm--url-regexp - (string-match helm--url-regexp path))) - basedir)))) - (when (and (string-match ":\\'" path) - (file-remote-p basedir nil t)) - (setq helm-pattern basedir)) - (cond ((string= path "Invalid tramp file name") - (or (helm-ff--tramp-hostnames) ; Hostnames completion. - (prog2 - ;; `helm-pattern' have not been modified yet. - ;; Set it here to the value of `path' that should be now - ;; "Invalid tramp file name" and set the candidates list - ;; to ("Invalid tramp file name") to make `helm-pattern' - ;; match single candidate "Invalid tramp file name". - (setq helm-pattern path) - ;; "Invalid tramp file name" is now printed - ;; in `helm-buffer'. - (list path)))) - ((or (and (file-regular-p path) - (eq last-repeatable-command 'helm-execute-persistent-action)) - ;; `ffap-url-regexp' don't match until url is complete. - (string-match helm-ff-url-regexp path) - invalid-basedir - (and (not (file-exists-p path)) (string-match "/$" path)) - (and helm--url-regexp (string-match helm--url-regexp path))) - (list path)) - ((string= path "") (helm-ff-directory-files "/")) - ;; Check here if directory is accessible (not working on Windows). - ((and (file-directory-p path) (not (file-readable-p path))) - (list (format "file-error: Opening directory permission denied `%s'" path))) - ;; A fast expansion of PATH is made only if `helm-ff-auto-update-flag' - ;; is enabled. - ((and dir-p helm-ff-auto-update-flag) - (helm-ff-directory-files path)) - (t (append (unless (or require-match - ;; Check here if path is an existing - ;; file before adding it to - ;; candidates, it was previously done - ;; in the sort function but this - ;; create a bug with remote files - ;; when path is at the same time a - ;; pattern matching a candidate and a - ;; real candidate e.g. ack and - ;; ack-grep in /usr/bin. This is due - ;; presumably to a latency more - ;; important with remote files which - ;; lead to a confusion with the - ;; pattern matching one candidate and - ;; the real candidate which is same - ;; as pattern. - (file-exists-p path) - ;; When `helm-ff-auto-update-flag' has been - ;; disabled, whe don't want PATH to be added on top - ;; if it is a directory. - dir-p) - (list path)) - (helm-ff-directory-files basedir)))))) - -(defun helm-list-directory (directory) - "List directory DIRECTORY. - -If DIRECTORY is remote use `helm-list-directory-function' otherwise use -`directory-files'." - (let* ((remote (file-remote-p directory 'method)) - (helm-list-directory-function - (if (and remote (not (string= remote "ftp"))) - helm-list-directory-function - #'helm-list-dir-lisp)) - (remote-fn-p (eq helm-list-directory-function - 'helm-list-dir-external)) - (sort-method (cl-case helm-ff-initial-sort-method - (newest (if (and remote remote-fn-p) - "-t" #'file-newer-than-file-p)) - (size (if (and remote remote-fn-p) - "-S" #'helm-ff-file-larger-that-file-p)) - (t nil)))) - (if remote - (funcall helm-list-directory-function directory sort-method) - (if sort-method - (sort (directory-files directory t directory-files-no-dot-files-regexp) - sort-method) - (directory-files directory t directory-files-no-dot-files-regexp))))) - -(defsubst helm-ff-file-larger-that-file-p (f1 f2) - (let ((attr1 (file-attributes f1)) - (attr2 (file-attributes f2))) - (> (nth 7 attr1) (nth 7 attr2)))) - -(defun helm-list-dir-lisp (directory &optional sort-method) - "List DIRECTORY with `file-name-all-completions' as backend. - -Add a `helm-ff-dir' property on each fname ending with \"/\"." - ;; NOTE: `file-name-all-completions' and `directory-files' and most - ;; tramp file handlers don't handle cntrl characters in fnames, so - ;; the displayed files will be plain wrong in this case, even worst - ;; the filenames will be splitted in two or more filenames. - (cl-loop for f in (sort (file-name-all-completions "" directory) - (or sort-method 'string-lessp)) - unless (or (string= f "") - (member f '("./" "../")) - ;; Ignore the tramp names from / - ;; completion, e.g. ssh: scp: etc... - (char-equal (aref f (1- (length f))) ?:)) - if (and (helm--dir-name-p f) - (helm--dir-file-name f directory)) - collect (propertize it 'helm-ff-dir t) - else collect (propertize (expand-file-name f directory) - 'helm-ff-file t))) - -(defun helm-list-dir-external (dir &optional sort-method) - "List directory DIR with external shell command as backend. - -This function is fast enough to be used for remote files and save the -type of files at the same time in a property for using it later in the -transformer." - (let ((default-directory (file-name-as-directory - (expand-file-name dir)))) - (with-temp-buffer - (when (eq (process-file-shell-command - (format - ;; -A remove dot files, -F append [*=@|/>] at eof - ;; and -Q quote the real filename. If not using -Q, - ;; there is no way to distinguish if foo* is a real - ;; file or if it is foo the executable file so with - ;; -Q we have "foo"* for the executable file foo and - ;; "foo*" for the real file foo. The downside is - ;; that we need an extra step to remove the quotes - ;; at the end which impact performances. - "ls -A -1 -F -b -Q %s | awk -v dir=%s '{print dir $0}'" - (or sort-method "") - (shell-quote-argument default-directory)) - nil t nil) - 0) - (goto-char (point-min)) - (save-excursion - (while (re-search-forward "[*=@|/>]$" nil t) - ;; A line looks like /home/you/"foo"@ - (helm-acase (match-string 0) - ("*" (replace-match "") - (put-text-property - (point-at-bol) (point-at-eol) 'helm-ff-exe t)) - ("@" (replace-match "") - (put-text-property - (point-at-bol) (point-at-eol) 'helm-ff-sym t)) - ("/" (replace-match "") - (put-text-property - (point-at-bol) (point-at-eol) 'helm-ff-dir t)) - (("=" "|" ">") (replace-match ""))))) - (while (re-search-forward "[\"]" nil t) - (replace-match "")) - (add-text-properties (point-min) (point-max) '(helm-ff-file t)) - (split-string (buffer-string) "\n" t))))) - -(defun helm-ff-directory-files (directory) - "List contents of DIRECTORY. -Argument FULL mean absolute path. -It is same as `directory-files' but always returns the -dotted filename '.' and '..' even on root directories in Windows -systems." - (setq directory (file-name-as-directory - (expand-file-name directory))) - (let* (file-error - (ls (condition-case err - (helm-list-directory directory) - ;; Handle file-error from here for Windows - ;; because predicates like `file-readable-p' and friends - ;; seem broken on emacs for Windows systems (always returns t). - ;; This should never be called on GNU/Linux/Unix - ;; as the error is properly intercepted in - ;; `helm-find-files-get-candidates' by `file-readable-p'. - (file-error - (prog1 - (list (format "%s:%s" - (car err) - (mapconcat 'identity (cdr err) " "))) - (setq file-error t))))) - (dot (concat directory ".")) - (dot2 (concat directory ".."))) - (puthash directory (+ (length ls) 2) helm-ff--directory-files-hash) - (append (and (not file-error) (list dot dot2)) ls))) - -(defun helm-ff-handle-backslash (fname) - ;; Allow creation of filenames containing a backslash. - (cl-loop with bad = '((92 . "")) - for i across fname - if (assq i bad) concat (cdr it) - else concat (string i))) - -(defun helm-ff-fuzzy-matching-p () - (and helm-ff-fuzzy-matching - (not (memq helm-mm-matching-method '(multi1 multi3p))))) - -(defun helm-ff--transform-pattern-for-completion (pattern) - "Maybe return PATTERN with it's basename modified as a regexp. -This happen only when `helm-ff-fuzzy-matching' is enabled. -This provide a similar behavior as `ido-enable-flex-matching'. -See also `helm--mapconcat-pattern'. -If PATTERN is an url returns it unmodified. -When PATTERN contain a space fallback to multi-match. -If basename contain one or more space fallback to multi-match. -If PATTERN is a valid directory name,return PATTERN unchanged." - ;; handle bad filenames containing a backslash (no more needed in - ;; emacs-26, also prevent regexp matching with e.g. "\|"). - ;; (setq pattern (helm-ff-handle-backslash pattern)) - (let ((bn (helm-basename pattern)) - (bd (or (helm-basedir pattern) "")) - ;; Trigger tramp connection with file-directory-p. - (dir-p (file-directory-p pattern)) - (tramp-p (cl-loop for (m . f) in tramp-methods - thereis (string-match m pattern)))) - ;; Always regexp-quote base directory name to handle - ;; crap dirnames such e.g bookmark+ - (cond - ((or (and dir-p tramp-p (string-match ":\\'" pattern)) - (string= pattern "") - (and dir-p (<= (length bn) 2)) - ;; Fix Issue #541 when BD have a subdir similar - ;; to BN, don't switch to match plugin - ;; which will match both. - (and dir-p (string-match (regexp-quote bn) bd))) - ;; Use full PATTERN on e.g "/ssh:host:". - (regexp-quote pattern)) - ;; Prefixing BN with a space call multi-match completion. - ;; This allow showing all files/dirs matching BN (Issue #518). - ;; FIXME: some multi-match methods may not work here. - (dir-p (concat (regexp-quote bd) " " (regexp-quote bn))) - ((or (not (helm-ff-fuzzy-matching-p)) - (string-match "\\s-" bn)) ; Fall back to multi-match. - (concat (regexp-quote bd) bn)) - ((or (string-match "[*][.]?.*" bn) ; Allow entering wilcard. - (string-match "/$" pattern) ; Allow mkdir. - (string-match helm-ff-url-regexp pattern) - (and (string= helm-ff-default-directory "/") tramp-p)) - ;; Don't treat wildcards ("*") as regexp char. - ;; (e.g ./foo/*.el => ./foo/[*].el) - (concat (regexp-quote bd) - (replace-regexp-in-string "[*]" "[*]" bn))) - (t (concat (regexp-quote bd) - (if (>= (length bn) 2) ; wait 2nd char before concating. - (helm--mapconcat-pattern bn) - (concat ".*" (regexp-quote bn)))))))) - -(defun helm-dir-is-dot (dir) - (string-match "\\(?:/\\|\\`\\)\\.\\{1,2\\}\\'" dir)) - -(defun helm-ff-save-history () - "Store the last value of `helm-ff-default-directory' in `helm-ff-history'. -Note that only existing directories are saved here." - (when (and helm-ff-default-directory - (helm-file-completion-source-p) - (file-directory-p helm-ff-default-directory)) - (set-text-properties 0 (length helm-ff-default-directory) - nil helm-ff-default-directory) - (push helm-ff-default-directory helm-ff-history))) -(add-hook 'helm-cleanup-hook 'helm-ff-save-history) - -(defun helm-files-save-file-name-history (&optional force) - "Save marked files to `file-name-history'." - (let* ((src (helm-get-current-source)) - (src-name (assoc-default 'name src))) - (when (or force (helm-file-completion-source-p src) - (member src-name helm-files-save-history-extra-sources)) - (let ((mkd (helm-marked-candidates :with-wildcard t)) - (history-delete-duplicates t)) - (cl-loop for sel in mkd - when (and sel - (stringp sel) - (file-exists-p sel) - (not (file-directory-p sel))) - do - ;; we use `abbreviate-file-name' here because - ;; other parts of Emacs seems to, - ;; and we don't want to introduce duplicates. - (add-to-history 'file-name-history - (abbreviate-file-name sel))))))) -(add-hook 'helm-exit-minibuffer-hook 'helm-files-save-file-name-history) - -(defun helm-ff-valid-symlink-p (file) - (helm-aif (condition-case-unless-debug nil - ;; `file-truename' send error - ;; on cyclic symlinks (Issue #692). - (file-truename file) - (error nil)) - (file-exists-p it))) - -(defun helm-get-default-mode-for-file (filename) - "Return the default mode to open FILENAME." - (let ((mode (cl-loop for (r . m) in auto-mode-alist - thereis (and (string-match r filename) m)))) - (or (and (symbolp mode) mode) "Fundamental"))) - -(defun helm-ff-properties (candidate) - "Show file properties of CANDIDATE in a tooltip or message." - (require 'helm-external) ; For `helm-get-default-program-for-file'. - (helm-aif (helm-file-attributes candidate) - (let* ((dired-line (helm-file-attributes - candidate :dired t :human-size t)) - (type (cl-getf it :type)) - (mode-type (cl-getf it :mode-type)) - (owner (cl-getf it :uid)) - (owner-right (cl-getf it :user t)) - (group (cl-getf it :gid)) - (group-right (cl-getf it :group)) - (other-right (cl-getf it :other)) - (trash (and (helm-ff-trash-file-p candidate) - (helm-ff--get-dest-file-from-trash - (helm-ff-trash-list) - (replace-regexp-in-string - "\\.trashinfo\\'" "" candidate)))) - (size (helm-file-human-size (cl-getf it :size))) - (modif (cl-getf it :modif-time)) - (access (cl-getf it :access-time)) - (ext (helm-get-default-program-for-file candidate)) - (tooltip-hide-delay (or helm-tooltip-hide-delay tooltip-hide-delay))) - (if (and (display-graphic-p) tooltip-mode) - (tooltip-show - (concat - (helm-basename candidate) "\n" - dired-line "\n" - (format "Mode: %s\n" (helm-get-default-mode-for-file candidate)) - (format "Ext prog: %s\n" (or (and ext (replace-regexp-in-string - " %s" "" ext)) - "Not defined")) - (format "Type: %s: %s\n" type mode-type) - (when (string= type "symlink") - (format "True name: '%s'\n" - (cond ((string-match "^\.#" (helm-basename candidate)) - "Autosave symlink") - ((helm-ff-valid-symlink-p candidate) - (file-truename candidate)) - (t "Invalid Symlink")))) - (format "Owner: %s: %s\n" owner owner-right) - (format "Group: %s: %s\n" group group-right) - (format "Others: %s\n" other-right) - (format "Size: %s\n" size) - (format "Modified: %s\n" modif) - (format "Accessed: %s\n" access) - (and (stringp trash) - (format "Trash: %s\n" - (abbreviate-file-name trash))))) - (message dired-line) (sit-for 5))) - (message "Permission denied, file not readable"))) - -(defun helm-ff-properties-persistent () - "Show properties without quitting helm." - (interactive) - (with-helm-alive-p - (helm-attrset 'properties-action '(helm-ff-properties . never-split)) - (helm-execute-persistent-action 'properties-action))) -(put 'helm-ff-properties-persistent 'helm-only t) - -(defun helm-ff-persistent-delete () - "Delete current candidate without quitting." - (interactive) - (with-helm-alive-p - (helm-attrset 'quick-delete '(helm-ff-quick-delete . never-split)) - (helm-execute-persistent-action 'quick-delete))) -(put 'helm-ff-persistent-delete 'helm-only t) - -(defun helm-ff-dot-file-p (file) - "Check if FILE is `.' or `..'." - (member (helm-basename file) '("." ".."))) - -(defun helm-ff-kill-buffer-fname (candidate) - (let* ((buf (get-file-buffer candidate)) - (buf-name (buffer-name buf))) - (cond ((and buf (eq buf (get-buffer helm-current-buffer))) - (user-error - "Can't kill `helm-current-buffer' without quitting session")) - (buf (kill-buffer buf) (message "Buffer `%s' killed" buf-name)) - (t (message "No buffer to kill"))))) - -(defun helm-ff-kill-or-find-buffer-fname (candidate) - "Find file CANDIDATE or kill it's buffer if it is visible. -Never kill `helm-current-buffer'. -Never kill buffer modified. -This is called normally on third hit of \ -\\\\[helm-execute-persistent-action] -in `helm-find-files-persistent-action-if'." - (let* ((buf (get-file-buffer candidate)) - (buf-name (buffer-name buf)) - (win (get-buffer-window buf)) - (helm--reading-passwd-or-string t)) - (cond ((and buf win (eq buf (get-buffer helm-current-buffer))) - (user-error - "Can't kill `helm-current-buffer' without quitting session")) - ((and buf win (buffer-modified-p buf)) - (message "Can't kill modified buffer, please save it before")) - ((and buf win) - (kill-buffer buf) - (if (and helm-persistent-action-display-window - (window-dedicated-p (next-window win 1))) - (delete-window helm-persistent-action-display-window) - (set-window-buffer win helm-current-buffer)) - (message "Buffer `%s' killed" buf-name)) - (t (find-file candidate))))) - -(defun helm-ff-run-kill-buffer-persistent () - "Execute `helm-ff-kill-buffer-fname' without quitting." - (interactive) - (with-helm-alive-p - (helm-attrset 'kill-buffer-fname 'helm-ff-kill-buffer-fname) - (helm-execute-persistent-action 'kill-buffer-fname))) -(put 'helm-ff-run-kill-buffer-persistent 'helm-only t) - -;; Preview with external tool -(defun helm-ff-persistent-open-file-externally (file) - (require 'helm-external) - (if (helm-get-default-program-for-file file) - (helm-open-file-externally file) - (message "Please configure an external program for `*%s' file in `helm-external-programs-associations'" - (file-name-extension file t)))) - -(defun helm-ff-run-preview-file-externally () - (interactive) - (with-helm-alive-p - (helm-attrset 'open-file-externally '(helm-ff-persistent-open-file-externally . never-split)) - (helm-execute-persistent-action 'open-file-externally))) -(put 'helm-ff-run-preview-file-externally 'helm-only t) - -(defun helm-ff-prefix-filename (fname &optional file-or-symlinkp new-file) - "Return filename FNAME maybe prefixed with [?] or [@]. -If FILE-OR-SYMLINKP is non--nil this mean we assume FNAME is an -existing filename or valid symlink and there is no need to test it. -NEW-FILE when non--nil mean FNAME is a non existing file and -return FNAME prefixed with [?]." - (let* ((prefix-new (propertize - " " 'display - (propertize "[?]" 'face 'helm-ff-prefix))) - (prefix-url (propertize - " " 'display - (propertize "[@]" 'face 'helm-ff-prefix)))) - (cond (file-or-symlinkp fname) - ((or (string-match helm-ff-url-regexp fname) - (and helm--url-regexp (string-match helm--url-regexp fname))) - (concat prefix-url " " fname)) - (new-file (concat prefix-new " " fname))))) - -(defun helm-ff-score-candidate-for-pattern (real disp pattern) - (if (or (member real '("." "..")) - ;; Incomplete filenames are prefixed with two spaces, the - ;; first one beeing propertized with a 'display prop - ;; i.e. "[?] foo". - (and (string-match-p "\\`\\s-\\{2\\}" disp) - (string= real (substring-no-properties disp 2)))) - 900000 - (helm-score-candidate-for-pattern real pattern))) - -(defun helm-ff-sort-candidates-1 (candidates input) - "Sort function for `helm-source-find-files'. -Return candidates prefixed with basename of INPUT first." - (if (or (and (file-directory-p input) - (string-match "/\\'" input)) - (string-match "\\`\\$" input) - (null candidates)) - candidates - (let* ((memo-src (make-hash-table :test 'equal)) - (all (sort candidates - (lambda (s1 s2) - (let* ((score (lambda (disp real) - (helm-ff-score-candidate-for-pattern - disp real (helm-basename input)))) - ;; Reals - (r1 (helm-basename (if (consp s1) (cdr s1) s1))) - (r2 (helm-basename (if (consp s2) (cdr s2) s2))) - ;; Displays - (d1 (helm-basename (if (consp s1) (car s1) s1))) - (d2 (helm-basename (if (consp s2) (car s2) s2))) - (sc1 (or (gethash r1 memo-src) - (puthash r1 (funcall score r1 d1) memo-src))) - (sc2 (or (gethash r2 memo-src) - (puthash r2 (funcall score r2 d2) memo-src)))) - (cond ((= sc1 sc2) - (< (string-width r1) - (string-width r2))) - ((> sc1 sc2)))))))) - all))) - -(defun helm-ff-sort-candidates (candidates _source) - "Sort function for `helm-source-find-files'. -Return candidates prefixed with basename of `helm-input' first." - (helm-ff-sort-candidates-1 candidates helm-input)) - -(defun helm-ff-boring-file-p (file) - ;; Prevent user doing silly thing like - ;; adding the dotted files to boring regexps (#924). - (and helm-ff-skip-boring-files - (not (string-match "\\.$" file)) - (string-match helm-ff--boring-regexp file))) - -(defvar helm-ff--git-found-p nil) -(defun helm-ff-git-ignored-p (file) - (and helm-ff-skip-git-ignored-files - (not (file-remote-p file)) - (or helm-ff--git-found-p - (setq helm-ff--git-found-p (executable-find "git"))) - (zerop (call-process "git" nil nil nil "check-ignore" "-q" file)))) - -(defun helm-ff-filter-candidate-one-by-one (file) - "`filter-one-by-one' Transformer function for `helm-source-find-files'." - ;; Handle boring files - (let ((basename (helm-basename file)) - dot) - (unless (or (helm-ff-boring-file-p basename) - (helm-ff-git-ignored-p file)) - - ;; Handle tramp files with minimal highlighting. - (if (and (or (string-match-p helm-tramp-file-name-regexp helm-pattern) - (helm-file-on-mounted-network-p helm-pattern))) - (let* (hostp - (disp (if (and helm-ff-transformer-show-only-basename - (not (setq dot (helm-dir-is-dot file)))) - (or (setq hostp - (helm-ff--get-host-from-tramp-invalid-fname - file)) - basename) - file))) - ;; Filename with cntrl chars e.g. foo^J - ;; This will not work as long as most tramp file handlers doesn't - ;; handle such case, e.g. file-name-all-completions, - ;; directory-files, file-name-nondirectory etc... - ;; Keep it though in case they fix this upstream... - (setq disp (replace-regexp-in-string "[[:cntrl:]]" "?" disp)) - (cond (;; Dot directories . and .. - dot (propertize file 'face 'helm-ff-dotted-directory)) - ;; Directories. - ((get-text-property 1 'helm-ff-dir file) - (cons (propertize disp 'face 'helm-ff-directory) file)) - ;; Executable files. - ((get-text-property 1 'helm-ff-exe file) - (cons (propertize disp 'face 'helm-ff-executable) file)) - ;; Symlinks. - ((get-text-property 1 'helm-ff-sym file) - (cons (propertize disp 'face 'helm-ff-symlink) file)) - ;; Regular files. - ((get-text-property 1 'helm-ff-file file) - (cons (propertize disp 'face 'helm-ff-file) file)) - ;; non existing files. - (t (cons (helm-ff-prefix-filename - (propertize disp 'face 'helm-ff-file) - hostp (unless hostp 'new-file)) - file)))) - - ;; Highlight local files showing everything, symlinks, exe, - ;; dirs etc... - (let* ((disp (if (and helm-ff-transformer-show-only-basename - (not (setq dot (helm-dir-is-dot file))) - (not (and helm--url-regexp - (string-match helm--url-regexp file))) - (not (string-match helm-ff-url-regexp file))) - (or (helm-ff--get-host-from-tramp-invalid-fname file) - basename) - file)) - (attr (file-attributes file)) - (type (car attr)) - x-bit) - ;; Filename cntrl chars e.g. foo^J - (setq disp (replace-regexp-in-string "[[:cntrl:]]" "?" disp)) - (cond ((string-match "file-error" file) file) - (;; A dead symlink. - (and (stringp type) - (not (helm-ff-valid-symlink-p file)) - (not (string-match "^\\.#" basename))) - (cons (propertize disp 'face 'helm-ff-invalid-symlink) - file)) - ;; A dotted directory symlinked. - ((and dot (stringp type)) - (cons (propertize disp 'face 'helm-ff-dotted-symlink-directory) - file)) - ;; A dotted directory. - ((helm-ff-dot-file-p file) - (cons (propertize disp 'face 'helm-ff-dotted-directory) - file)) - ;; A symlink. - ((stringp type) - (cons (propertize disp 'display - (concat (propertize disp 'face 'helm-ff-symlink) - " -> " - (propertize (abbreviate-file-name type) - 'face 'helm-ff-truename))) - file)) - ;; A directory. - ((eq t type) - (cons (propertize disp 'face 'helm-ff-directory) - file)) - ;; A character device file. - ((and attr (string-match - "\\`[cp]" (setq x-bit (substring (nth 8 attr) 0 4)))) - (cons (propertize disp 'face 'helm-ff-pipe) - file)) - ;; A socket file. - ((and attr (string-match "\\`[s]" x-bit)) - (cons (propertize disp 'face 'helm-ff-socket) - file)) - ;; An executable file. - ((and attr - (string-match - "x\\'" x-bit)) - (cons (propertize disp 'face 'helm-ff-executable) - file)) - ;; An executable file with suid - ((and attr (string-match "s\\'" x-bit)) - (cons (propertize disp 'face 'helm-ff-suid) - file)) - ;; A file. - ((and attr (null type)) - (cons (propertize disp 'face 'helm-ff-file) - file)) - ;; A non--existing file. - (t (cons (helm-ff-prefix-filename - (propertize disp 'face 'helm-ff-file) nil 'new-file) - file)))))))) - -(defun helm-find-files-action-transformer (actions candidate) - "Action transformer for `helm-source-find-files'." - (let ((str-at-point (with-helm-current-buffer - (buffer-substring-no-properties - (point-at-bol) (point-at-eol))))) - (when (file-regular-p candidate) - (setq actions (helm-append-at-nth - actions '(("Checksum File" . helm-ff-checksum)) 4))) - (cond ((and (file-exists-p candidate) - (string-match "Trash/files/?\\'" (helm-basedir candidate)) - (not (member (helm-basename candidate) '("." ".."))) - (executable-find "trash")) - (helm-append-at-nth - actions - '(("Restore file(s) from trash" . helm-restore-file-from-trash) - ("Delete file(s) from trash" . helm-ff-trash-rm)) - 1)) - ((and helm--url-regexp - (not (string-match-p helm--url-regexp str-at-point)) - (not (with-helm-current-buffer (eq major-mode 'dired-mode))) - (string-match-p ":\\([0-9]+:?\\)" str-at-point)) - (append '(("Find file to line number" . helm-ff-goto-linum)) - actions)) - ((string-match (image-file-name-regexp) candidate) - (helm-append-at-nth - actions - '(("Rotate image right `M-r'" . helm-ff-rotate-image-right) - ("Rotate image left `M-l'" . helm-ff-rotate-image-left)) - 3)) - ((string-match "\\.el\\'" (helm-aif (helm-marked-candidates) - (car it) candidate)) - (helm-append-at-nth - actions - '(("Byte compile lisp file(s) `M-B, C-u to load'" - . helm-find-files-byte-compile) - ("Load File(s) `M-L'" . helm-find-files-load-files)) - 2)) - ((string-match "\\.elc?\\'" (helm-aif (helm-marked-candidates) - (car it) candidate)) - (helm-append-at-nth - actions - '(("Load File(s) `M-L'" . helm-find-files-load-files)) - 2)) - ((and (string-match "\\.html?$" candidate) - (file-exists-p candidate)) - (helm-append-at-nth - actions '(("Browse url file" . browse-url-of-file)) 2)) - ((or (string= (file-name-extension candidate) "pdf") - (string= (file-name-extension candidate) "PDF")) - (helm-append-at-nth - actions '(("Pdfgrep File(s)" . helm-ff-pdfgrep)) 4)) - (t actions)))) - -(defun helm-ff-trash-action (fn names &rest args) - "Execute a trash action FN on marked files. - -Arg NAMES is a list of strings to pass to messages -e.g. '(\"delete\" \"deleting\"), ARGS are other args to be passed to FN." - (let ((mkd (helm-marked-candidates)) - errors) - (with-helm-display-marked-candidates - helm-marked-buffer-name - (helm-ff--count-and-collect-dups (mapcar 'helm-basename mkd)) - (if (y-or-n-p (format "%s %s files from trash? " - (capitalize (car names)) - (length mkd))) - (progn - (message "%s files from trash..." (capitalize (cadr names))) - (cl-loop for f in mkd do - (condition-case err - (apply fn f args) - (error (push (format "%s" (cadr err)) errors) - nil))) - (if errors - (display-warning 'helm - (with-temp-buffer - (insert (format-time-string "%Y-%m-%d %H:%M:%S\n" - (current-time))) - (insert (format - "Failed to %s %s/%s files from trash\n" - (car names) (length errors) (length mkd))) - (insert (mapconcat 'identity errors "\n") "\n ") - (buffer-string)) - :error - "*helm restore warnings*") - (message "%s %s files from trash done" - (capitalize (cadr names)) (length mkd)))) - (message "Restoring files from trash aborted"))))) - -(defun helm-ff-trash-rm (_candidate) - "Delete marked-files from a Trash directory. - -The Trash directory should be a directory compliant with - and each file -should have its '*.trashinfo' correspondent file in Trash/info -directory." - (helm-ff-trash-action 'helm-ff-trash-rm-1 '("delete" "deleting"))) - -(defun helm-ff-trash-rm-1 (file) - (let ((info-file (concat (helm-reduce-file-name file 2) - "info/" (helm-basename file "trashinfo") - ".trashinfo"))) - (cl-assert (file-exists-p file) - nil (format "No such file or directory `%s'" - file)) - (cl-assert (file-exists-p info-file) - nil (format "No such file or directory `%s'" - info-file)) - (if (file-directory-p file) - (delete-directory file t) - (delete-file file)) - (delete-file info-file))) - -(defun helm-restore-file-from-trash (_candidate) - "Restore marked-files from a Trash directory. - -The Trash directory should be a directory compliant with - and each file -should have its '*.trashinfo' correspondent file in Trash/info -directory." - (let* ((default-directory (file-name-as-directory - helm-ff-default-directory)) - (trashed-files (helm-ff-trash-list))) - (helm-ff-trash-action 'helm-restore-file-from-trash-1 - '("restore" "restoring") - trashed-files))) - -(defun helm-restore-file-from-trash-1 (file trashed-files) - "Restore FILE from a trash directory. -Arg TRASHED-FILES is an alist of (fname_in_trash . dest) obtained with -`helm-ff-trash-list'." - ;; Emacs trash duplicate files with a unique name + .trashinfo in - ;; the filename which is wrong, only files in info directory should - ;; end with .trashinfo, so fix the filename before looking for dest name. - (let* ((fname (replace-regexp-in-string "\\.trashinfo\\'" "" file)) - (info-file (concat (helm-reduce-file-name fname 2) - "info/" - (helm-basename fname) - ".trashinfo")) - (dest-file (helm-ff--get-dest-file-from-trash - trashed-files fname))) - (cl-assert (not (file-exists-p dest-file)) nil - (format "File `%s' already exists" dest-file)) - (cl-assert dest-file nil "No such file in trash") - (rename-file file dest-file) - (delete-file info-file))) - -(defun helm-ff-trash-file-p (file) - "Return `t' when file is a trashed file." - (and (file-exists-p file) - (string-match "Trash/files/?\\'" (helm-basedir file)) - (not (member (helm-basename file) '("." ".."))))) - -(defun helm-ff--get-dest-file-from-trash (trashed-files file) - (assoc-default (helm-basename file) trashed-files)) - -(defun helm-ff-trash-list () - "Return an alist of trashed files basename and dest name." - (cl-loop for f in (directory-files - (expand-file-name - ;; helm-ff-default-directory is actually the - ;; trash directory. - "info" (helm-basedir (directory-file-name helm-ff-default-directory))) - t directory-files-no-dot-files-regexp) - collect (cons (helm-basename (replace-regexp-in-string "\\.trashinfo\\'" "" f)) - (with-temp-buffer - (save-excursion - (insert-file-contents f)) - (when (re-search-forward "^path=" nil t) - (helm-url-unhex-string - (buffer-substring-no-properties - (point) (point-at-eol)))))))) - -(defun helm-ff-goto-linum (candidate) - "Find file CANDIDATE and maybe jump to line number found in fname at point. -line number should be added at end of fname preceded with \":\". -e.g \"foo:12\"." - (let ((linum (with-helm-current-buffer - (let ((str (buffer-substring-no-properties - (point-at-bol) (point-at-eol)))) - (when (string-match ":\\([0-9]+:?\\)" str) - (match-string 1 str)))))) - (find-file candidate) - (and linum (not (string= linum "")) - (helm-goto-line (string-to-number linum) t)))) - -(defun helm-ff-mail-attach-files (_candidate) - "Run `mml-attach-file' on `helm-marked-candidates'." - (require 'mml) - (let ((flist (helm-marked-candidates :with-wildcard t)) - (dest-buf (and (derived-mode-p 'message-mode 'mail-mode) - (current-buffer))) - bufs) - (unless dest-buf - (setq bufs (cl-loop for b in (buffer-list) - when (with-current-buffer b - (derived-mode-p 'message-mode 'mail-mode)) - collect (buffer-name b))) - (if (and bufs (y-or-n-p "Attach files to existing mail composition buffer? ")) - (setq dest-buf - (if (cdr bufs) - (helm-comp-read "Attach to buffer: " bufs :nomark t) - (car bufs))) - (compose-mail) - (setq dest-buf (current-buffer)))) - (switch-to-buffer dest-buf) - (save-restriction - (widen) - (save-excursion - (goto-char (point-max)) - (cl-loop for f in flist - do (mml-attach-file f (or (mm-default-file-encoding f) - "application/octet-stream"))))))) - -(defvar image-dired-display-image-buffer) -(defun helm-ff-rotate-current-image-1 (file num-arg) - "Rotate current image at NUM-ARG degrees." - (setq file (file-truename file)) ; For symlinked images. - ;; When FILE is not an image-file, do nothing. - (when (and (file-exists-p file) - (string-match (image-file-name-regexp) file)) - (setq num-arg (if (string= helm-ff-rotate-image-program "exiftran") - (cl-case num-arg - (90 "-9") ; 90 clockwise - (270 "-2")) ; 270 clockwise == -90 - (number-to-string num-arg))) - (if (executable-find helm-ff-rotate-image-program) - (let ((default-directory (file-name-directory file)) - (basename (helm-basename file))) - (apply #'process-file helm-ff-rotate-image-program nil nil nil - (append helm-ff-rotate-image-switch - (list num-arg basename))) - (when (buffer-live-p image-dired-display-image-buffer) - (kill-buffer image-dired-display-image-buffer)) - (image-dired-display-image basename) - (message nil) - (display-buffer (get-buffer image-dired-display-image-buffer))) - (error "%s not found" helm-ff-rotate-image-program)))) - -(defun helm-ff-rotate-image-left (candidate) - "Rotate image file CANDIDATE left. -This affect directly file CANDIDATE." - (helm-ff-rotate-current-image-1 candidate 270)) - -(defun helm-ff-rotate-image-right (candidate) - "Rotate image file CANDIDATE right. -This affect directly file CANDIDATE." - (helm-ff-rotate-current-image-1 candidate 90)) - -(defun helm-ff-rotate-left-persistent () - "Rotate image left without quitting helm." - (interactive) - (with-helm-alive-p - (helm-attrset 'image-action1 'helm-ff-rotate-image-left) - (helm-execute-persistent-action 'image-action1))) -(put 'helm-ff-rotate-left-persistent 'helm-only t) - -(defun helm-ff-rotate-right-persistent () - "Rotate image right without quitting helm." - (interactive) - (with-helm-alive-p - (helm-attrset 'image-action2 'helm-ff-rotate-image-right) - (helm-execute-persistent-action 'image-action2))) -(put 'helm-ff-rotate-right-persistent 'helm-only t) - -(defun helm-ff-exif-data (candidate) - "Extract exif data from file CANDIDATE using `helm-ff-exif-data-program'." - (if (and helm-ff-exif-data-program - (executable-find helm-ff-exif-data-program)) - (shell-command-to-string (format "%s %s %s" - helm-ff-exif-data-program - helm-ff-exif-data-program-args - candidate)) - (format "No program %s found to extract exif" - helm-ff-exif-data-program))) - -(cl-defun helm-find-files-persistent-action-if (candidate) - "Open subtree CANDIDATE without quitting helm. -If CANDIDATE is not a directory expand CANDIDATE filename. -If CANDIDATE is alone, open file CANDIDATE filename. -That's mean: -First hit on C-j expand CANDIDATE second hit open file. -If a prefix arg is given or `helm-follow-mode' is on open file." - (let* ((follow (or (helm-follow-mode-p) - helm--temp-follow-flag)) - (image-cand (string-match-p (image-file-name-regexp) candidate)) - (new-pattern (helm-get-selection)) - (num-lines-buf (with-current-buffer helm-buffer - (count-lines (point-min) (point-max)))) - (insert-in-minibuffer (lambda (fname) - (with-selected-window (or (active-minibuffer-window) - (minibuffer-window)) - (unless follow - (delete-minibuffer-contents) - (set-text-properties 0 (length fname) - nil fname) - (insert fname)))))) - (helm-attrset 'candidate-number-limit helm-ff-candidate-number-limit) - (unless image-cand - (when follow - (helm-follow-mode -1) - (cl-return-from helm-find-files-persistent-action-if - (message "Helm-follow-mode allowed only on images, disabling")))) - (cond ((and (helm-ff--invalid-tramp-name-p) - (string-match helm-tramp-file-name-regexp candidate)) - (cons (lambda (_candidate) - ;; First hit insert hostname and - ;; second hit insert ":" and expand. - (if (string= candidate helm-pattern) - (funcall insert-in-minibuffer (concat candidate ":")) - (funcall insert-in-minibuffer candidate))) - 'never-split)) - (;; A symlink directory, expand it but not to its truename - ;; unless a prefix arg is given. - (and (file-directory-p candidate) (file-symlink-p candidate)) - (cons (lambda (_candidate) - (funcall insert-in-minibuffer - (file-name-as-directory - (if current-prefix-arg - (file-truename (expand-file-name candidate)) - (expand-file-name candidate))))) - 'never-split)) - ;; A directory, open it. - ((file-directory-p candidate) - (cons (lambda (_candidate) - (when (string= (helm-basename candidate) "..") - (setq helm-ff-last-expanded helm-ff-default-directory)) - (funcall insert-in-minibuffer (file-name-as-directory - (expand-file-name candidate)))) - 'never-split)) - ;; A symlink file, expand to it's true name. (first hit) - ((and (file-symlink-p candidate) (not current-prefix-arg) (not follow)) - (cons (lambda (_candidate) - (funcall insert-in-minibuffer (file-truename candidate)) - (helm-check-minibuffer-input)) ; Force update. - 'never-split)) - ;; A regular file, expand it, (first hit) - ((and (>= num-lines-buf 3) (not current-prefix-arg) (not follow)) - (cons (lambda (_candidate) - (funcall insert-in-minibuffer new-pattern) - (helm-check-minibuffer-input)) ; Force update. - 'never-split)) - ;; An image file and it is the second hit on C-j, - ;; show the file in `image-dired'. - (image-cand - (lambda (_candidate) - (require 'image-dired) - (let* ((win (get-buffer-window - image-dired-display-image-buffer 'visible)) - (fname (and win - (with-selected-window win - (get-text-property (point-min) - 'original-file-name)))) - (remove-buf-only (and win - fname - (with-helm-buffer - (file-equal-p candidate fname))))) - (when remove-buf-only - (with-helm-window - (if (and helm-persistent-action-display-window - (window-dedicated-p (next-window win 1))) - (delete-window helm-persistent-action-display-window) - (set-window-buffer win helm-current-buffer)))) - (when (buffer-live-p (get-buffer image-dired-display-image-buffer)) - (kill-buffer image-dired-display-image-buffer)) - (unless remove-buf-only - ;; Fix emacs bug never fixed upstream. - (unless (file-directory-p image-dired-dir) - (make-directory image-dired-dir)) - (switch-to-buffer image-dired-display-image-buffer) - (message "Resizing image...") - (cl-letf (((symbol-function 'message) #'ignore)) - (image-dired-display-image candidate)) - (message "Resizing image done") - (with-current-buffer image-dired-display-image-buffer - (let ((exif-data (helm-ff-exif-data candidate))) - (setq default-directory helm-ff-default-directory) - (image-dired-update-property 'help-echo exif-data))))))) - ;; Allow browsing archive on avfs fs. - ;; Assume volume is already mounted with mountavfs. - ((helm-aand helm-ff-avfs-directory - (file-name-directory candidate) - (string-match - (regexp-quote (expand-file-name helm-ff-avfs-directory)) - it) - (helm-ff-file-compressed-p candidate)) - (cons (lambda (_candidate) - (funcall insert-in-minibuffer (concat candidate "#/"))) - 'never-split)) - ;; File doesn't exists and basename starts with ".." or " ", - ;; Start a recursive search for directories. - ((and (not (file-exists-p candidate)) - (not (file-remote-p candidate)) - (string-match-p "\\`\\([.]\\|\\s-\\)\\{2\\}[^/]+" - (helm-basename candidate))) - ;; As soon as the final "/" is added the job is passed - ;; to `helm-ff-auto-expand-to-home-or-root'. - (cons (lambda (_candidate) - (funcall insert-in-minibuffer (concat candidate "/"))) - 'never-split)) - ;; File is not existing and have no basedir, typically when - ;; user hit C-k (minibuffer is empty) and then write foo and - ;; hit C-j. This make clear that when no basedir, helm will - ;; create the file in default-directory. - ((and (not (file-exists-p candidate)) - (not (helm-basedir candidate))) - (cons (lambda (_candidate) - (funcall insert-in-minibuffer - (expand-file-name candidate default-directory))) - 'never-split)) - ;; On second hit we open file. - ;; On Third hit we kill it's buffer maybe. - (t - (lambda (_candidate) - (funcall helm-ff-kill-or-find-buffer-fname-fn candidate)))))) - - -;;; Recursive dirs completion -;; -(defun helm-find-files-recursive-dirs (directory &optional input) - (when (string-match "\\(\\s-+\\|[.]\\)\\{2\\}" input) - (setq input (replace-match "" nil t input))) - (message "Recursively searching %s from %s ..." - input (abbreviate-file-name directory)) - ;; Ensure to not create a new frame - (let (helm-actions-inherit-frame-settings) - (helm :sources - (helm-make-source - "Recursive directories" 'helm-locate-subdirs-source - :basedir (if (string-match-p - "\\`es" helm-locate-recursive-dirs-command) - directory - (shell-quote-argument directory)) - :subdir (shell-quote-argument input) - :candidate-transformer - `((lambda (candidates) - (cl-loop for c in candidates - when (and (file-directory-p c) - (null (helm-boring-directory-p - c helm-boring-file-regexp-list)) - (string-match-p ,(regexp-quote input) - (helm-basename c))) - collect (propertize c 'face 'helm-ff-dirs))) - helm-w32-pathname-transformer - (lambda (candidates) - (helm-ff-sort-candidates-1 candidates ,input))) - :persistent-action 'ignore - :action (lambda (c) - (helm-set-pattern - (file-name-as-directory (expand-file-name c))))) - :candidate-number-limit 999999 - :allow-nest t - :resume 'noresume - :ff-transformer-show-only-basename nil - :buffer "*helm recursive dirs*"))) - -(defun helm-ff-recursive-dirs (_candidate) - "Launch a recursive search in `helm-ff-default-directory'." - (with-helm-default-directory helm-ff-default-directory - (helm-find-files-recursive-dirs - (helm-current-directory) - (helm-basename (helm-get-selection))))) - -(defun helm-ff-file-compressed-p (candidate) - "Whether CANDIDATE is a compressed file or not." - (member (file-name-extension candidate) - helm-ff-file-compressed-list)) - -(defun helm-ff--fname-at-point () - "Try to guess fname at point." - (let ((end (point)) - (limit (helm-aif (bounds-of-thing-at-point 'filename) - (car it) - (point)))) - (save-excursion - (while (re-search-backward "\\(~\\|/\\|[[:lower:][:upper:]]:/\\)" - limit t)) - (buffer-substring-no-properties (point) end)))) - -(defun helm-insert-file-name-completion-at-point (_candidate) - "Insert file name completion at point. - -When completing i.e. there is already something at point, insert -filename abbreviated, relative or full according to initial input, -whereas when inserting i.e. there is nothing at point, insert filename -full, abbreviated or relative according to prefix arg, respectively no -prefix arg, one prefix arg or two prefix arg." - (with-helm-current-buffer - (if buffer-read-only - (error "Error: Buffer `%s' is read-only" (buffer-name)) - (let* ((mkds (helm-marked-candidates :with-wildcard t)) - (candidate (car mkds)) - (end (point)) - (tap (helm-ffap-guesser)) - (guess (and (stringp tap) - (substring-no-properties tap))) - (beg (if guess (- (point) (length guess)) (point))) - (full-path-p (and (stringp guess) - (or (string-match-p - (concat "^" (getenv "HOME")) - guess) - (string-match-p - "\\`\\(/\\|[[:lower:][:upper:]]:/\\)" - guess)))) - (escape-fn (with-helm-current-buffer - (if (memq major-mode - helm-modes-using-escaped-strings) - #'shell-quote-argument #'identity)))) - (insert - (funcall escape-fn (helm-ff--insert-fname - candidate beg end full-path-p guess)) - (if (cdr mkds) " " "") - (mapconcat escape-fn - (cl-loop for f in (cdr mkds) - collect (helm-ff--insert-fname f)) - " ")))))) - -(defun helm-ff--insert-fname (candidate &optional beg end full-path guess) - (set-text-properties 0 (length candidate) nil candidate) - (if (and beg end guess (not (string= guess "")) - (or (string-match - "^\\(~/\\|/\\|[[:lower:][:upper:]]:/\\)" - guess) - (file-exists-p candidate))) - (prog1 - (cond (full-path - (expand-file-name candidate)) - ((string= (match-string 1 guess) "~/") - (abbreviate-file-name candidate)) - (t (file-relative-name candidate))) - (delete-region beg end)) - (helm-acase helm-current-prefix-arg - ('(4) (abbreviate-file-name candidate)) - ('(16) (file-relative-name candidate)) - ('(64) (helm-basename candidate)) - (t candidate)))) - -(cl-defun helm-find-files-history (arg &key (comp-read t)) - "The `helm-find-files' history. -Show the first `helm-ff-history-max-length' elements of -`helm-ff-history' in an `helm-comp-read'." - (interactive "p") - (let ((history (when helm-ff-history - (helm-fast-remove-dups helm-ff-history - :test 'equal)))) - (when history - (setq helm-ff-history - (if (>= (length history) helm-ff-history-max-length) - (cl-subseq history 0 helm-ff-history-max-length) - history)) - (if comp-read - (let ((src (helm-build-sync-source "Helm Find Files History" - :candidates helm-ff-history - :fuzzy-match (helm-ff-fuzzy-matching-p) - :persistent-action 'ignore - :migemo t - :action (lambda (candidate) - (if arg - (helm-set-pattern - (expand-file-name candidate)) - (identity candidate)))))) - (helm :sources src - :resume 'noresume - :buffer helm-ff-history-buffer-name - :allow-nest t)) - helm-ff-history)))) -(put 'helm-find-files-history 'helm-only t) - -(defun helm-find-files-1 (fname &optional preselect) - "Find FNAME filename with PRESELECT filename preselected. - -Use it for non--interactive calls of `helm-find-files'." - (require 'tramp) - ;; Resolve FNAME now outside of helm. - ;; [FIXME] When `helm-find-files-1' is used directly from lisp - ;; and FNAME is an abbreviated path, for some reasons - ;; `helm-update' is called many times before resolving - ;; the abbreviated path (Issue #1939) so be sure to pass a - ;; full path to helm-find-files-1. - (unless (string-match-p helm-ff-url-regexp fname) - (setq fname (expand-file-name (substitute-in-file-name fname)))) - (when (get-buffer helm-action-buffer) - (kill-buffer helm-action-buffer)) - (setq helm-find-files--toggle-bookmark nil) - (let* ( ;; Be sure we don't erase the precedent minibuffer if some. - (helm-ff-auto-update-initial-value - (and helm-ff-auto-update-initial-value - (not (minibuffer-window-active-p (minibuffer-window))))) - (tap (thing-at-point 'filename)) - (def (and tap (or (file-remote-p tap) - (expand-file-name tap))))) - (helm-set-local-variable 'helm-follow-mode-persistent nil) - (unless helm-source-find-files - (setq helm-source-find-files (helm-make-source - "Find Files" 'helm-source-ffiles))) - (when (helm-attr 'follow helm-source-find-files) - (helm-attrset 'follow -1 helm-source-find-files)) - (helm-ff-setup-update-hook) - (add-hook 'helm-resume-after-hook 'helm-ff--update-resume-after-hook) - (unwind-protect - (helm :sources 'helm-source-find-files - :input fname - :case-fold-search helm-file-name-case-fold-search - :preselect preselect - :ff-transformer-show-only-basename - helm-ff-transformer-show-only-basename - :default def - :prompt "Find files or url: " - :buffer "*helm find files*") - (helm-ff--update-resume-after-hook nil t) - (setq helm-ff-default-directory nil)))) - -(defun helm-ff--update-resume-after-hook (sources &optional nohook) - "Meant to be used in `helm-resume-after-hook'. -When NOHOOK is non nil run inconditionally, otherwise only when source -is helm-source-find-files." - (when (or nohook (string= "Find Files" - (assoc-default 'name (car sources)))) - (helm-attrset 'resume `(lambda () - (helm-ff-setup-update-hook) - (setq helm-ff-default-directory - ,helm-ff-default-directory - helm-ff-last-expanded - ,helm-ff-last-expanded)) - helm-source-find-files))) - -(defun helm-ff-clean-initial-input () - ;; When using hff in an external frame initial input is printed in - ;; the minibuffer of initial-frame, delete it. - (with-selected-frame helm-initial-frame - (helm-clean-up-minibuffer))) - -(defun helm-ff-setup-update-hook () - (dolist (hook '(helm-ff-clean-initial-input ; Add to be called first. - helm-ff-move-to-first-real-candidate - helm-ff-update-when-only-one-matched - helm-ff-auto-expand-to-home-or-root)) - (add-hook 'helm-after-update-hook hook))) - -(defun helm-find-files-cleanup () - (mapc (lambda (hook) - (remove-hook 'helm-after-update-hook hook)) - '(helm-ff-auto-expand-to-home-or-root - helm-ff-update-when-only-one-matched - helm-ff-move-to-first-real-candidate - helm-ff-clean-initial-input))) - -(defun helm-ff-bookmark () - (helm :sources 'helm-source-bookmark-helm-find-files - :buffer "*helm ff bookmarks*")) - -(defun helm-find-files-switch-to-bookmark () - "Switch to helm-bookmark for `helm-find-files' from `helm-find-files.'" - (interactive) - (require 'helm-bookmark) - (with-helm-alive-p - (helm-run-after-exit 'helm-ff-bookmark))) -(put 'helm-find-files-switch-to-bookmark 'helm-only t) - -(defun helm-find-files-initial-input (&optional input) - "Return INPUT if present, otherwise try to guess it." - (let ((guesser (helm-acase (helm-ffap-guesser) - ("" nil) - (t it)))) - (unless (eq major-mode 'image-mode) - (or (and input (or (and (file-remote-p input) input) - (expand-file-name input))) - (helm-find-files-input - (if (and helm-ff-allow-non-existing-file-at-point - guesser - (not (string-match ffap-url-regexp guesser))) - ;; Keep the ability of jumping to numbered lines even - ;; when allowing non existing filenames at point. - (helm-aand guesser - (thing-at-point 'filename) - (replace-regexp-in-string - ":[0-9]+\\'" "" it)) - guesser) - (thing-at-point 'filename)))))) - -(defun helm-ffap-guesser () - "Same as `ffap-guesser' but without gopher and machine support." - (require 'ffap) - ;; Avoid "Stack overflow in regexp matcher" error - ;; in evil `ffap-guesser' by removing crap `ffap-gopher-at-point' - ;; (bug fixed in emacs-26 #25391) . - ;; `ffap-machine-at-point' have been removed too as it was anyway - ;; disabled with `ffap-machine-p-known' bound to 'reject. - ;; `ffap-file-at-point' can be neutralized with - ;; `helm-ff-guess-ffap-filenames' and `ffap-url-at-point' with - ;; `helm-ff-guess-ffap-urls' - ;; Note also that `ffap-url-unwrap-remote' can override these - ;; variables. - (let ((ffap-alist (and helm-ff-guess-ffap-filenames ffap-alist)) - (ffap-url-regexp helm--url-regexp)) - (if (eq major-mode 'dired-mode) - (let ((beg (save-excursion (dired-move-to-filename))) - (end (save-excursion (dired-move-to-end-of-filename t)))) - (helm-aif (and beg end (member (buffer-substring beg end) - '("." ".."))) - (concat (file-name-as-directory - (expand-file-name dired-directory)) - (car it)) - (dired-get-filename 'no-dir t))) - (let* ((beg (and (use-region-p) (region-beginning))) - (end (and (use-region-p) (region-end))) - (str (and beg end (buffer-substring-no-properties beg end))) - (ffap (or (helm-aand helm-ff-guess-ffap-urls ffap-url-regexp - (ffap-fixup-url (ffap-url-at-point)) - (and (string-match ffap-url-regexp it) it)) - (ffap-file-at-point)))) - ;; Workaround emacs bugs: - ;; When the region is active and a file is detected - ;; `ffap-string-at-point' returns the region prefixed with - ;; "/", e.g. at a beginning of a patch (first bug) and make - ;; `file-remote-p' returning an error (second bug), so in such - ;; case returns the region itself instead of the region - ;; corrupted by ffap. - (if (and str ffap) str ffap))))) - -(defun helm-find-files-input (file-at-pt thing-at-pt) - "Try to guess a default input for `helm-find-files'." - (let* ((non-essential t) - (remp (or (and file-at-pt (file-remote-p file-at-pt)) - (and thing-at-pt (file-remote-p thing-at-pt)))) - (def-dir (helm-current-directory)) - (urlp (and file-at-pt helm--url-regexp - (string-match helm--url-regexp file-at-pt))) - (lib (when helm-ff-search-library-in-sexp - (helm-find-library-at-point))) - (hlink (helm-ff-find-url-at-point)) - (file-p (and file-at-pt - (not (string= file-at-pt "")) - (not remp) - (or (file-exists-p file-at-pt) - helm-ff-allow-non-existing-file-at-point) - (not urlp) - thing-at-pt - (not (string= thing-at-pt "")) - (file-exists-p - (file-name-directory - (expand-file-name thing-at-pt def-dir)))))) - (cond (lib) ; e.g we are inside a require sexp. - (hlink) ; String at point is an hyperlink. - (file-p ; a regular file - (and file-at-pt (if (not (member (helm-basename file-at-pt) - '("." ".."))) - (expand-file-name file-at-pt) - file-at-pt))) - (urlp (helm-html-decode-entities-string file-at-pt)) ; possibly an url or email. - ((and file-at-pt - (not remp) - (or helm-ff-allow-non-existing-file-at-point - (file-exists-p file-at-pt))) - (expand-file-name file-at-pt))))) - -(defun helm-ff-find-url-at-point () - "Try to find link to an url in text-property at point." - (let* ((he (get-text-property (point) 'help-echo)) - (ov (overlays-at (point))) - (ov-he (and ov (overlay-get - (car (overlays-at (point))) 'help-echo))) - (w3m-l (get-text-property (point) 'w3m-href-anchor)) - (nt-prop (get-text-property (point) 'nt-link))) - ;; Org link. - (when (and (stringp he) (string-match "^LINK: " he)) - (setq he (replace-match "" t t he))) - (cl-loop for i in (list he ov-he w3m-l nt-prop) - thereis (and (stringp i) helm--url-regexp (string-match helm--url-regexp i) i)))) - -(defun helm-find-library-at-point () - "Try to find library path at point. -Find inside `require' and `declare-function' sexp." - (require 'find-func) - (let* ((beg-sexp (save-excursion (search-backward "(" (point-at-bol) t))) - (end-sexp (save-excursion (search-forward ")" (point-at-eol) t))) - (sexp (and beg-sexp end-sexp - (buffer-substring-no-properties - (1+ beg-sexp) (1- end-sexp))))) - (ignore-errors - (cond ((and sexp (string-match "require ['].+[^)]" sexp)) - (find-library-name - (replace-regexp-in-string - "'\\|)\\|(" "" - ;; If require use third arg, ignore it, - ;; always use library path found in `load-path'. - (cl-second (split-string (match-string 0 sexp)))))) - ((and sexp (string-match-p "^declare-function" sexp)) - (find-library-name - (replace-regexp-in-string - "\"\\|ext:" "" - (cl-third (split-string sexp))))) - (t nil))))) - - -;;; Handle copy, rename, symlink, relsymlink and hardlink from helm. -;; -;; -(defun helm-ff--valid-default-directory () - (with-helm-current-buffer - (cl-loop for b in (buffer-list) - for cd = (with-current-buffer b default-directory) - when (eq (car (file-attributes cd)) t) - return cd))) - -(cl-defun helm-dired-action (candidate - &key action follow (files (dired-get-marked-files))) - "Execute ACTION on FILES to CANDIDATE. -Where ACTION is a symbol that can be one of: -'copy, 'rename, 'symlink,'relsymlink, 'hardlink or 'backup. -Argument FOLLOW when non--nil specify to follow FILES to destination for the actions -copy and rename." - (require 'dired-async) - (require 'dired-x) ; For dired-keep-marker-relsymlink - (when (get-buffer dired-log-buffer) (kill-buffer dired-log-buffer)) - ;; When default-directory in current-buffer is an invalid directory, - ;; (e.g buffer-file directory have been renamed somewhere else) - ;; be sure to use a valid value to give to dired-create-file. - ;; i.e start-process is creating a process buffer based on default-directory. - (let ((default-directory (helm-ff--valid-default-directory)) - (fn (cl-case action - (copy 'dired-copy-file) - (rename 'dired-rename-file) - (symlink 'make-symbolic-link) - (relsymlink 'dired-make-relative-symlink) - (hardlink 'dired-hardlink) - (backup 'backup-file))) - (marker (cl-case action - ((copy rename backup) dired-keep-marker-copy) - (symlink dired-keep-marker-symlink) - (relsymlink dired-keep-marker-relsymlink) - (hardlink dired-keep-marker-hardlink))) - (dirflag (and (= (length files) 1) - (file-directory-p (car files)) - (not (file-directory-p candidate)))) - (dired-async-state (if (and (boundp 'dired-async-mode) - dired-async-mode) - 1 -1))) - (and follow (fboundp 'dired-async-mode) (dired-async-mode -1)) - (when (and (cdr files) (not (file-directory-p candidate))) - (error "%s: target `%s' is not a directory" action candidate)) - (unwind-protect - (dired-create-files - fn (symbol-name action) files - ;; CANDIDATE is the destination. - (if (file-directory-p candidate) - ;; When CANDIDATE is a directory, build file-name in this directory. - ;; Else we use CANDIDATE. - (lambda (from) - (expand-file-name (file-name-nondirectory from) candidate)) - (lambda (_from) candidate)) - marker) - (and (fboundp 'dired-async-mode) - (dired-async-mode dired-async-state))) - (push (file-name-as-directory - (if (file-directory-p candidate) - (expand-file-name candidate) - (file-name-directory candidate))) - helm-ff-history) - ;; If follow is non--nil we should not be in async mode. - (when (and follow - (not (memq action '(symlink relsymlink hardlink))) - (not (get-buffer dired-log-buffer))) - (let ((target (directory-file-name candidate))) - (unwind-protect - (progn - (setq helm-ff-cand-to-mark - (helm-get-dest-fnames-from-list files candidate dirflag)) - (with-helm-after-update-hook (helm-ff-maybe-mark-candidates)) - (if (and dirflag (eq action 'rename)) - (helm-find-files-1 (file-name-directory target) - (if helm-ff-transformer-show-only-basename - (helm-basename target) target)) - (helm-find-files-1 (file-name-as-directory - (expand-file-name candidate))))) - (setq helm-ff-cand-to-mark nil)))))) - -(defun helm-get-dest-fnames-from-list (flist dest-cand rename-dir-flag) - "Transform filenames of FLIST to abs of DEST-CAND. -If RENAME-DIR-FLAG is non--nil collect the `directory-file-name' of transformed -members of FLIST." - ;; At this point files have been renamed/copied at destination. - ;; That's mean DEST-CAND exists. - (cl-loop - with dest = (expand-file-name dest-cand) - for src in flist - for basename-src = (helm-basename src) - for fname = (cond (rename-dir-flag (directory-file-name dest)) - ((file-directory-p dest) - (concat (file-name-as-directory dest) basename-src)) - (t dest)) - when (file-exists-p fname) - collect fname into tmp-list - finally return (sort tmp-list 'string<))) - -(defun helm-ff-maybe-mark-candidates () - "Mark all candidates of list `helm-ff-cand-to-mark'. -This is used when copying/renaming/symlinking etc... and -following files to destination." - (when (and (string= (assoc-default 'name (helm-get-current-source)) - (assoc-default 'name helm-source-find-files)) - helm-ff-cand-to-mark) - (with-helm-window - (while helm-ff-cand-to-mark - (if (string= (car helm-ff-cand-to-mark) (helm-get-selection)) - (progn - (helm-make-visible-mark) - (helm-next-line) - (setq helm-ff-cand-to-mark (cdr helm-ff-cand-to-mark))) - (helm-next-line))) - (unless (helm-this-visible-mark) - (helm-prev-visible-mark))))) - - -;;; Routines for files -;; -;; -(defun helm-file-buffers (filename) - "Returns a list of buffer names corresponding to FILENAME." - (cl-loop with name = (expand-file-name filename) - for buf in (buffer-list) - for bfn = (buffer-file-name buf) - when (and bfn (string= name bfn)) - collect (buffer-name buf))) - -(defun helm-ff--delete-by-moving-to-trash (file) - "Decide to trash or delete FILE. -Returns non-nil when FILE needs to be trashed." - (let ((remote (file-remote-p file))) - (or - (and delete-by-moving-to-trash - (null helm-current-prefix-arg) - (null current-prefix-arg) - (or (and remote helm-trash-remote-files) - (null remote))) - (and (null delete-by-moving-to-trash) - (or helm-current-prefix-arg - current-prefix-arg) - (or (and remote helm-trash-remote-files) - (null remote)))))) - -(defun helm-ff-quick-delete (_candidate) - "Delete file CANDIDATE without quitting. - -When a prefix arg is given, meaning of `delete-by-moving-to-trash' is -inversed." - (with-helm-window - (let ((marked (helm-marked-candidates))) - (unwind-protect - (cl-loop with trash = (helm-ff--delete-by-moving-to-trash (car marked)) - for c in marked do - (progn (helm-preselect - (concat "^" (regexp-quote - (if (and helm-ff-transformer-show-only-basename - (not (helm-ff-dot-file-p c))) - (helm-basename c) c)))) - (when (y-or-n-p - (format "Really %s file `%s'? " - (if trash "Trash" "Delete") - (abbreviate-file-name c))) - (helm-delete-file - c helm-ff-signal-error-on-dot-files 'synchro trash) - (helm-delete-current-selection) - (message nil) - (helm--remove-marked-and-update-mode-line c)))) - (setq helm-marked-candidates nil - helm-visible-mark-overlays nil) - (helm-force-update - (let ((presel (helm-get-selection))) - (when presel - (concat "^" (regexp-quote (if (and helm-ff-transformer-show-only-basename - (not (helm-ff-dot-file-p presel))) - (helm-basename presel) presel)))))))))) - -(defun helm-delete-file (file &optional error-if-dot-file-p synchro trash) - "Delete FILE after querying the user. - -When a prefix arg is given, meaning of `delete-by-moving-to-trash' is -inversed. - -Return error when ERROR-IF-DOT-FILE-P is non nil and user tries to -delete a dotted file i.e. \".\" or \"..\". - -Ask user when directory are not empty to allow recursive deletion -unless `helm-ff-allow-recursive-deletes' is non nil. -When user is asked and reply with \"!\" don't ask for remaining -directories. - -Ask to kill buffers associated with that file, too. - -When TRASH is non nil, trash FILE even if `delete-by-moving-to-trash' -is nil." - (require 'dired) - (cl-block nil - (when (and error-if-dot-file-p - (helm-ff-dot-file-p file)) - (error "Error: Cannot operate on `.' or `..'")) - (let ((buffers (helm-file-buffers file)) - (helm--reading-passwd-or-string t) - (file-attrs (file-attributes file)) - (trash (or trash (helm-ff--delete-by-moving-to-trash file))) - (delete-by-moving-to-trash trash)) - (cond ((and (eq (nth 0 file-attrs) t) - (directory-files file t dired-re-no-dot)) - ;; Synchro means persistent deletion from HFF. - (if synchro - (when (or helm-ff-allow-recursive-deletes - trash - (y-or-n-p (format "Recursive delete of `%s'? " - (abbreviate-file-name file)))) - (delete-directory file 'recursive trash)) - ;; Avoid using dired-delete-file really annoying in - ;; emacs-26 but allows using ! (instead of all) to not - ;; confirm anymore for recursive deletion of - ;; directory. This is not persistent for all session - ;; like emacs-26 does with dired-delete-file (think it - ;; is a bug). - (if (or helm-ff-allow-recursive-deletes trash) - (delete-directory file 'recursive trash) - (helm-acase (helm-read-answer (format "Recursive delete of `%s'? [y,n,!,q]" - (abbreviate-file-name file)) - '("y" "n" "!" "q")) - ("y" (delete-directory file 'recursive trash)) - ("!" (setq helm-ff-allow-recursive-deletes t) - (delete-directory file 'recursive trash)) - ("n" (cl-return 'skip)) - ("q" (throw 'helm-abort-delete-file - (progn - (message "Abort file deletion") (sleep-for 1)))))))) - ((eq (nth 0 file-attrs) t) - (delete-directory file nil trash)) - (t (delete-file file trash))) - (when buffers - (cl-dolist (buf buffers) - (when (y-or-n-p (format "Kill buffer %s, too? " buf)) - (kill-buffer buf))))))) - -(defun helm-delete-marked-files (_ignore) - "Delete marked files with `helm-delete-file'. - -When a prefix arg is given, meaning of `delete-by-moving-to-trash' is -inversed." - (let* ((files (helm-marked-candidates :with-wildcard t)) - (len 0) - (trash (helm-ff--delete-by-moving-to-trash (car files))) - (prmt (if trash "Trash" "Delete")) - (old--allow-recursive-deletes helm-ff-allow-recursive-deletes)) - (with-helm-display-marked-candidates - helm-marked-buffer-name - (helm-ff--count-and-collect-dups files) - (if (not (y-or-n-p (format "%s *%s File(s)" prmt (length files)))) - (message "(No deletions performed)") - (catch 'helm-abort-delete-file - (unwind-protect - (cl-dolist (i files) - (set-text-properties 0 (length i) nil i) - (let ((res (helm-delete-file - i helm-ff-signal-error-on-dot-files nil trash))) - (if (eq res 'skip) - (progn (message "Directory is not empty, skipping") - (sleep-for 1)) - (cl-incf len)))) - (setq helm-ff-allow-recursive-deletes old--allow-recursive-deletes))) - (message "%s File(s) %s" len (if trash "trashed" "deleted")))))) - -;;; Delete files async -;; -;; -(defvar helm-ff-delete-log-file - (expand-file-name "helm-delete-file.log" user-emacs-directory) - "The file use to communicate with emacs child when deleting files async.") - -(defvar helm-ff--trash-flag nil) - -(define-minor-mode helm-ff--delete-async-modeline-mode - "Notify mode-line that an async process run." - :group 'dired-async - :global t - ;; FIXME: Handle jobs like in dired-async, needs first to allow - ;; naming properly processes in async, they are actually all named - ;; emacs and running `async-batch-invoke', so if one copy a file and - ;; delete another file at the same time it may clash. - :lighter (:eval (propertize (format " %s file(s) async ..." - (if helm-ff--trash-flag - "Trashing" "Deleting")) - 'face 'helm-delete-async-message)) - (unless helm-ff--delete-async-modeline-mode - (let ((visible-bell t)) (ding)) - (setq helm-ff--trash-flag nil))) - -(defun helm-delete-async-mode-line-message (text face &rest args) - "Notify end of async operation in `mode-line'." - (message nil) - (let ((mode-line-format (concat - " " (propertize - (if args - (apply #'format text args) - text) - 'face face)))) - (force-mode-line-update) - (sit-for 3) - (force-mode-line-update))) - -(defun helm-delete-marked-files-async (_ignore) - "Same as `helm-delete-marked-files' but async. - -When a prefix arg is given, meaning of `delete-by-moving-to-trash' is -inversed. - -This function is not using `helm-delete-file' and BTW not asking user -for recursive deletion of directory, be warned that directories are -always deleted with no warnings." - (let* ((files (helm-marked-candidates :with-wildcard t)) - (trash (helm-ff--delete-by-moving-to-trash (car files))) - (prmt (if trash "Trash" "Delete")) - (buffers (cl-loop for file in files - for buf = (helm-file-buffers file) - when buf append buf)) - (callback (lambda (result) - (helm-ff--delete-async-modeline-mode -1) - (when (file-exists-p helm-ff-delete-log-file) - (display-warning 'helm - (with-temp-buffer - (insert-file-contents - helm-ff-delete-log-file) - (buffer-string)) - :error - "*helm delete files*") - (fit-window-to-buffer (get-buffer-window - "*helm delete files*")) - (delete-file helm-ff-delete-log-file)) - (when buffers - (dolist (buf buffers) - (let ((last-nonmenu-event t)) - (when (y-or-n-p (format "Kill buffer %s, too? " buf)) - (kill-buffer buf))))) - (run-with-timer - 0.1 nil - (lambda () - (helm-delete-async-mode-line-message - "%s (%s/%s) file(s) async done" - 'helm-delete-async-message - (if trash "Trashing" "Deleting") - result (length files)))))) - ;; Workaround emacs-26 bug with tramp see - ;; https://github.com/jwiegley/emacs-async/issues/80. - (async-quiet-switch "-q")) - (setq helm-ff--trash-flag trash) - (with-helm-display-marked-candidates - helm-marked-buffer-name - (helm-ff--count-and-collect-dups files) - (if (not (y-or-n-p (format "%s *%s File(s)" prmt (length files)))) - (message "(No deletions performed)") - (async-start - `(lambda () - ;; `delete-by-moving-to-trash' have to be set globally, - ;; using the TRASH argument of delete-file or - ;; delete-directory is not enough. - (setq delete-by-moving-to-trash ,trash) - (let ((result 0)) - (dolist (file ',files result) - (condition-case err - (cond ((eq (nth 0 (file-attributes file)) t) - (delete-directory file 'recursive ,trash) - (setq result (1+ result))) - (t (delete-file file ,trash) - (setq result (1+ result)))) - (error (with-temp-file ,helm-ff-delete-log-file - (insert (format-time-string "%x:%H:%M:%S\n")) - (insert (format "%s:%s\n " - (car err) - (mapconcat 'identity (cdr err) " "))))))))) - callback) - (helm-ff--delete-async-modeline-mode 1))))) - -(defun helm-find-file-or-marked (candidate) - "Open file CANDIDATE or open helm marked files in separate windows. -Called with one prefix arg open files in separate windows in a -vertical split. -Called with two prefix arg open files in background without selecting them." - (let ((marked (helm-marked-candidates :with-wildcard t)) - (url-p (and helm--url-regexp ; we should have only one candidate. - (string-match helm--url-regexp candidate))) - (ffap-newfile-prompt helm-ff-newfile-prompt-p) - (find-file-wildcards nil) - (helm--reading-passwd-or-string t)) - (if (cdr marked) - (if (equal helm-current-prefix-arg '(16)) - (mapcar 'find-file-noselect marked) - ;; If helm-current-prefix-arg is detected split is done - ;; vertically. - (helm-window-show-buffers (mapcar 'find-file-noselect marked))) - (let ((dir (and (not url-p) (helm-basedir candidate)))) - (cond ((and dir (file-directory-p dir)) - (find-file (substitute-in-file-name candidate))) - (url-p (find-file-at-point candidate)) - ;; A a non--existing filename ending with / - ;; Create a directory and jump to it. - ((and (not (file-exists-p candidate)) - (string-match "/$" candidate)) - (helm-ff--mkdir candidate 'helm-ff)) - ;; A non--existing filename NOT ending with / or - ;; an existing filename, create or jump to it. - ;; If the basedir of candidate doesn't exists, - ;; ask for creating it. - (dir - (helm-ff--mkdir dir) - (find-file candidate)) - ;; Find file at `default-directory' when basedir is - ;; unspecified e.g user hit C-k foo RET. - (t (find-file candidate))))))) - -(defun helm-ff-find-file-other-tab () - "Run find file in other tab action from `helm-source-buffers-list'." - (interactive) - (cl-assert (fboundp 'tab-bar-mode) nil "Tab-bar-mode not available") - (with-helm-alive-p - (helm-exit-and-execute-action 'find-file-other-tab))) -(put 'helm-ff-find-file-other-tab 'helm-only t) - -(defun helm-ff--mkdir (dir &optional helm-ff) - (when (or (not confirm-nonexistent-file-or-buffer) - (y-or-n-p (format "Create directory `%s'? " - (abbreviate-file-name - (expand-file-name dir))))) - (let ((dirfname (directory-file-name dir))) - (if (file-exists-p dirfname) - (error - "Mkdir: Unable to create directory `%s': file exists." - (helm-basename dirfname)) - (make-directory dir 'parent))) - (when helm-ff - ;; Allow having this new dir in history - ;; to be able to retrieve it immediately - ;; if we want to e.g copy a file from somewhere in it. - (setq helm-ff-default-directory - (file-name-as-directory (expand-file-name dir))) - (push helm-ff-default-directory helm-ff-history)) - (or (and helm-ff (helm-find-files-1 dir)) t))) - -(defun helm-transform-file-load-el (actions candidate) - "Add action to load the file CANDIDATE if it is an emacs lisp -file. Else return ACTIONS unmodified." - (if (member (file-name-extension candidate) '("el" "elc")) - (append actions '(("Load Emacs Lisp File" . load-file))) - actions)) - -(defun helm-transform-file-browse-url (actions candidate) - "Add an action to browse the file CANDIDATE if it is a html file or URL. -Else return ACTIONS unmodified." - (let ((browse-action '("Browse with Browser" . browse-url))) - (cond ((string-match "^http\\|^ftp" candidate) - (cons browse-action actions)) - ((string-match "\\.html?$" candidate) - (append actions (list browse-action))) - (t actions)))) - -(defun helm-file-on-mounted-network-p (file) - "Returns non-nil when FILE is part of a mounted remote directory. - -This function is checking `helm-mounted-network-directories' list." - (when helm-mounted-network-directories - (cl-loop for dir in helm-mounted-network-directories - thereis (file-in-directory-p file dir)))) - -;; helm-find-files bindings for filecache -(defvar file-cache-alist) - -(defun helm-ff-cache-add-file (_candidate) - (require 'filecache) - (let ((mkd (helm-marked-candidates :with-wildcard t))) - (mapc 'file-cache-add-file mkd))) - -(defun helm-ff-file-cache-remove-file-1 (file) - "Remove FILE from `file-cache-alist'." - (let ((entry (assoc (helm-basename file) file-cache-alist)) - (dir (helm-basedir file)) - new-entry) - (setq new-entry (remove dir entry)) - (when (= (length entry) 1) - (setq new-entry nil)) - (setq file-cache-alist - (cons new-entry (remove entry file-cache-alist))))) - -(defun helm-ff-file-cache-remove-file (_file) - "Remove marked files from `file-cache-alist.'" - (let ((mkd (helm-marked-candidates))) - (mapc 'helm-ff-file-cache-remove-file-1 mkd))) - - -;;; File name history -;; -;; -(defvar helm-source-file-name-history - (helm-build-sync-source "File Name History" - :candidates 'file-name-history - :persistent-action #'ignore - :filtered-candidate-transformer #'helm-file-name-history-transformer - :action 'helm-type-file-actions)) - -(defvar helm-source--ff-file-name-history nil - "[Internal] This source is build to be used with `helm-find-files'. -Don't use it in your own code unless you know what you are doing.") - -(defvar helm--file-name-history-hide-deleted nil) - -(defun helm-file-name-history-show-or-hide-deleted () - (interactive) - (setq helm--file-name-history-hide-deleted - (not helm--file-name-history-hide-deleted)) - (helm-update)) -(put 'helm-file-name-history-show-or-hide-deleted 'helm-only t) - -(defvar helm-file-name-history-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "C-c d") 'helm-file-name-history-show-or-hide-deleted) - map)) - -(defun helm-file-name-history-transformer (candidates _source) - (cl-loop for c in candidates - when (cond ((or (file-remote-p c) - (and (fboundp 'tramp-archive-file-name-p) - (tramp-archive-file-name-p c))) - (cons (propertize c 'face 'helm-history-remote) c)) - ((file-exists-p c) - (cons (propertize c 'face 'helm-ff-file) c)) - (t (unless helm--file-name-history-hide-deleted - (cons (propertize c 'face 'helm-history-deleted) c)))) - collect it)) - -(defun helm-ff-file-name-history () - "Switch to `file-name-history' without quitting `helm-find-files'." - (interactive) - (unless helm-source--ff-file-name-history - (setq helm-source--ff-file-name-history - (helm-build-sync-source "File name history" - :init (lambda () - (with-helm-alive-p - (require 'tramp-archive nil t) - (when helm-ff-file-name-history-use-recentf - (require 'recentf) - (or recentf-mode (recentf-mode 1))))) - :candidates (lambda () - (if helm-ff-file-name-history-use-recentf - recentf-list - file-name-history)) - :help-message 'helm-file-name-history-help-message - :fuzzy-match t - :persistent-action 'ignore - :migemo t - :filtered-candidate-transformer 'helm-file-name-history-transformer - :action (helm-make-actions - "Find file" (lambda (candidate) - (helm-set-pattern - (expand-file-name candidate)) - (with-helm-after-update-hook (helm-exit-minibuffer))) - "Find file in helm" (lambda (candidate) - (helm-set-pattern - (expand-file-name candidate)))) - :keymap helm-file-name-history-map))) - (with-helm-alive-p - (helm :sources 'helm-source--ff-file-name-history - :buffer "*helm-file-name-history*" - :allow-nest t - :resume 'noresume))) -(put 'helm-ff-file-name-history 'helm-only t) - -;;; Browse project -;; Need dependencies: -;; -;; -;; Only hg and git are supported for now. -(defvar helm--browse-project-cache (make-hash-table :test 'equal)) -(defvar helm-buffers-in-project-p) - -(defvar helm-browse-project-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-generic-files-map) - (define-key map (kbd "M-g a") 'helm-browse-project-run-ag) - map)) - -(defun helm-browse-project-get-buffers (root-directory) - (cl-loop for b in (helm-buffer-list) - ;; FIXME: Why default-directory is root-directory - ;; for current-buffer when coming from helm-quit-and-find-file. - for cd = (with-current-buffer b default-directory) - for bn = (buffer-file-name (get-buffer b)) - if (or (and bn (file-in-directory-p bn root-directory)) - (and (null bn) - (not (file-remote-p cd)) - (file-in-directory-p cd root-directory))) - collect b)) - -(defun helm-browse-project-build-buffers-source (directory) - (helm-make-source "Buffers in project" 'helm-source-buffers - :header-name (lambda (name) - (format - "%s (%s)" - name (abbreviate-file-name directory))) - :buffer-list (lambda () (helm-browse-project-get-buffers directory)))) - -(defun helm-browse-project-walk-directory (directory) - "Default function for `helm-browse-project-default-find-files-fn'." - (helm-walk-directory - directory - :directories nil :path 'full :skip-subdirs t)) - -(defun helm-browse-project-find-files-1 (directory program) - "List files in DIRECTORY recursively with external PROGRAM." - (let ((cmd (cl-ecase program - (ag "ag --hidden -g '.*' %s") - (rg "rg --files --hidden -g '*' %s")))) - (with-temp-buffer - (call-process-shell-command - (format cmd directory) - nil t nil) - (mapcar (lambda (f) (expand-file-name f directory)) - (split-string (buffer-string) "\n"))))) - -(defun helm-browse-project-ag-find-files (directory) - "A suitable function for `helm-browse-project-default-find-files-fn'. -Use AG as backend." - (helm-browse-project-find-files-1 directory 'ag)) - -(defun helm-browse-project-rg-find-files (directory) - "A suitable function for `helm-browse-project-default-find-files-fn'. -Use RG as backend." - (helm-browse-project-find-files-1 directory 'rg)) - -(defun helm-browse-project-ag (_candidate) - "helm-grep AG action for helm-browse-project." - (let ((dir (with-helm-buffer (helm-attr 'root-dir)))) - (helm-grep-ag dir helm-current-prefix-arg))) - -(defun helm-browse-project-run-ag () - "Runs helm-grep AG from helm-browse-project." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-browse-project-ag))) -(put 'helm-browse-project-run-ag 'helm-only t) - -(defclass helm-browse-project-override-inheritor (helm-type-file) ()) - -(defclass helm-browse-project-source (helm-source-in-buffer - helm-browse-project-override-inheritor) - ((root-dir :initarg :root-dir - :initform nil - :custom 'file) - (match-part :initform - (lambda (c) - (if (with-helm-buffer - helm-ff-transformer-show-only-basename) - (helm-basename c) c))) - (filter-one-by-one :initform - (lambda (c) - (if (with-helm-buffer - helm-ff-transformer-show-only-basename) - (cons (propertize (helm-basename c) - 'face 'helm-ff-file) - c) - (propertize c 'face 'helm-ff-file))))) - "Class to define a source in helm-browse-project handling non VC -handled directories.") - -(defmethod helm--setup-source :after ((source helm-browse-project-override-inheritor)) - (let ((actions (slot-value source 'action))) - (setf (slot-value source 'action) - (helm-append-at-nth - (symbol-value actions) - '(("Grep project with AG `M-g a, C-u select type'" . helm-browse-project-ag)) - 7)) - (setf (slot-value source 'keymap) helm-browse-project-map))) - -(defun helm-browse-project-find-files (directory &optional refresh) - "Browse non VC handled directory DIRECTORY." - (when refresh (remhash directory helm--browse-project-cache)) - (unless (gethash directory helm--browse-project-cache) - (puthash directory (funcall helm-browse-project-default-find-files-fn - directory) - helm--browse-project-cache)) - (helm :sources `(,(helm-browse-project-build-buffers-source directory) - ,(helm-make-source "Browse project" - 'helm-browse-project-source - :root-dir directory - :data (gethash directory helm--browse-project-cache) - :header-name - (lambda (name) - (format - "%s (%s)" - name (abbreviate-file-name directory))))) - :ff-transformer-show-only-basename nil - :buffer "*helm browse project*")) - -(defvar helm-browse-project-history nil) - -;;;###autoload -(defun helm-projects-history (arg) - (interactive "P") - (helm :sources - (helm-build-sync-source "Project history" - :candidates helm-browse-project-history - :action (lambda (candidate) - (with-helm-default-directory candidate - (helm-browse-project - (or arg helm-current-prefix-arg))))) - :buffer "*helm browse project history*")) - -;;;###autoload -(defun helm-browse-project (arg) - "Preconfigured helm to browse projects. -Browse files and see status of project with its vcs. -Only HG and GIT are supported for now. -Fall back to `helm-browse-project-find-files' -if current directory is not under control of one of those vcs. -With a prefix ARG browse files recursively, with two prefix ARG -rebuild the cache. -If the current directory is found in the cache, start -`helm-browse-project-find-files' even with no prefix ARG. -NOTE: The prefix ARG have no effect on the VCS controlled directories. - -Needed dependencies for VCS: - -and -." - (interactive "P") - (require 'helm-x-files) - (let ((helm-type-buffer-actions - (remove (assoc "Browse project from buffer" - helm-type-buffer-actions) - helm-type-buffer-actions)) - (helm-buffers-in-project-p t)) - (cl-flet ((push-to-hist (root) - (setq helm-browse-project-history - (cons root (delete root helm-browse-project-history))))) - (helm-acond ((and (require 'helm-ls-git nil t) - (fboundp 'helm-ls-git-root-dir) - (helm-ls-git-root-dir)) - (push-to-hist it) - (helm-ls-git-ls)) - ((and (require 'helm-ls-hg nil t) - (fboundp 'helm-hg-root) - (helm-hg-root)) - (push-to-hist it) - (helm-hg-find-files-in-project)) - ((helm-browse-project-get--root-dir (helm-current-directory)) - (if (or arg (gethash it helm--browse-project-cache)) - (progn - (push-to-hist it) - (helm-browse-project-find-files it (equal arg '(16)))) - (helm :sources (helm-browse-project-build-buffers-source it) - :buffer "*helm browse project*"))))))) - -(defun helm-browse-project-get--root-dir (directory) - (cl-loop with dname = (file-name-as-directory directory) - while (and dname (not (gethash dname helm--browse-project-cache))) - if (file-remote-p dname) - do (setq dname nil) else - do (setq dname (helm-basedir (substring dname 0 (1- (length dname))))) - finally return (or dname (file-name-as-directory directory)))) - -(defun helm-ff-browse-project (_candidate) - "Browse project in current directory. -See `helm-browse-project'." - (with-helm-default-directory helm-ff-default-directory - (helm-browse-project helm-current-prefix-arg))) - -(defun helm-ff-run-browse-project () - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-ff-browse-project))) -(put 'helm-ff-run-browse-project 'helm-only t) - -(defun helm-ff-gid (_candidate) - (with-helm-default-directory helm-ff-default-directory - (helm-gid))) - -(defun helm-ff-run-gid () - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-ff-gid))) -(put 'helm-ff-run-gid 'helm-only t) - -;; helm-find bindings for helm-find-files. -(defun helm-ff-find-sh-command (_candidate) - "Run `helm-find' from `helm-find-files'." - (require 'helm-find) - (helm-find-1 helm-ff-default-directory)) - -(defun helm-ff-run-find-sh-command () - "Run find shell command action with key from `helm-find-files'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-ff-find-sh-command))) -(put 'helm-ff-run-find-sh-command 'helm-only t) - - -;;;###autoload -(defun helm-find-files (arg) - "Preconfigured `helm' for helm implementation of `find-file'. -Called with a prefix arg show history if some. -Don't call it from programs, use `helm-find-files-1' instead. -This is the starting point for nearly all actions you can do on files." - (interactive "P") - (let* ((hist (and arg helm-ff-history (helm-find-files-history nil))) - (smart-input (or hist (helm-find-files-initial-input))) - (default-input (expand-file-name (helm-current-directory))) - (input (cond ((and (null hist) - helm-find-files-ignore-thing-at-point) - default-input) - ((and (eq major-mode 'org-agenda-mode) - org-directory - (not smart-input)) - (file-name-as-directory - (expand-file-name org-directory))) - ((and (eq major-mode 'dired-mode) smart-input) - (file-name-directory smart-input)) - ((and (not (string= smart-input "")) - smart-input)) - (t default-input))) - (input-as-presel (null (nth 0 (file-attributes input)))) - (presel (helm-aif (or hist - (and input-as-presel input) - (buffer-file-name (current-buffer)) - (and (eq major-mode 'dired-mode) - smart-input)) - (if (and helm-ff-transformer-show-only-basename - (null hist) - (not (string-match-p "[.]\\{1,2\\}\\'" it))) - (helm-basename it) it)))) - ;; Continue using the same display function as history which used - ;; probably itself the same display function as inner HFF call, - ;; i.e. if history was using frame use a frame otherwise use a window. - (when (and hist (buffer-live-p (get-buffer helm-ff-history-buffer-name))) - (helm-set-local-variable 'helm-display-function - (with-current-buffer helm-ff-history-buffer-name - helm-display-function) - 'helm--last-frame-parameters - (with-current-buffer helm-ff-history-buffer-name - helm--last-frame-parameters))) - (set-text-properties 0 (length input) nil input) - (setq current-prefix-arg nil) - ;; Allow next helm session to reuse helm--last-frame-parameters as - ;; resume would do. - (let ((helm--executing-helm-action (not (null hist)))) - (helm-find-files-1 input (and presel (null helm-ff-no-preselect) - (concat "^" (regexp-quote presel))))))) - -;;;###autoload -(defun helm-delete-tramp-connection () - "Allow deleting tramp connection or marked tramp connections at once. - -This replace `tramp-cleanup-connection' which is partially broken in -emacs < to 25.1.50.1 (See Emacs Bug#24432). - -It allows additionally to delete more than one connection at once." - (interactive) - (let ((helm-quit-if-no-candidate - (lambda () - (message "No Tramp connection found")))) - (helm :sources (helm-build-sync-source "Tramp connections" - :candidates (tramp-list-connections) - :candidate-transformer (lambda (candidates) - (cl-loop for v in candidates - for name = (apply #'tramp-make-tramp-file-name - (cl-loop with v = (helm-ff--tramp-cons-or-vector v) - for i across v collect i)) - when (or (processp (tramp-get-connection-process v)) - (buffer-live-p (get-buffer (tramp-buffer-name v)))) - collect (cons name v))) - :action (lambda (_vec) - (let ((vecs (helm-marked-candidates))) - (cl-loop for v in vecs - do (progn - (tramp-cleanup-connection v) - (remhash v tramp-cache-data)))))) - :buffer "*helm tramp connections*"))) - - -(provide 'helm-files) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-files.el ends here diff --git a/elpa/helm-20191031.725/helm-find.el b/elpa/helm-20191031.725/helm-find.el deleted file mode 100644 index 9c1ab0ca..00000000 --- a/elpa/helm-20191031.725/helm-find.el +++ /dev/null @@ -1,175 +0,0 @@ -;;; helm-find.el --- helm interface for find command. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'helm-files) -(require 'helm-external) - -(defcustom helm-findutils-skip-boring-files t - "Ignore boring files in find command results." - :group 'helm-files - :type 'boolean) - -(defcustom helm-findutils-search-full-path nil - "Search in full path with shell command find when non--nil. -I.e use the -path/ipath arguments of find instead of -name/iname." - :group 'helm-files - :type 'boolean) - -(defcustom helm-find-noerrors nil - "Prevent showing error messages in helm buffer when non nil." - :group 'helm-files - :type 'boolean) - -(defvar helm-find-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-generic-files-map) - (define-key map (kbd "DEL") 'helm-delete-backward-no-update) - map)) - -(defvar helm-source-findutils - (helm-build-async-source "Find" - :header-name (lambda (name) - (concat name " in [" (helm-default-directory) "]")) - :candidates-process 'helm-find-shell-command-fn - :filtered-candidate-transformer 'helm-findutils-transformer - :action-transformer 'helm-transform-file-load-el - :persistent-action 'helm-ff-kill-or-find-buffer-fname - :action 'helm-type-file-actions - :help-message 'helm-generic-file-help-message - :keymap helm-find-map - :candidate-number-limit 9999 - :requires-pattern 3)) - -(defun helm-findutils-transformer (candidates _source) - (let (non-essential - (default-directory (helm-default-directory))) - (cl-loop for i in candidates - for abs = (expand-file-name - (helm-aif (file-remote-p default-directory) - (concat it i) i)) - for type = (car (file-attributes abs)) - for disp = (if (and helm-ff-transformer-show-only-basename - (not (string-match "[.]\\{1,2\\}$" i))) - (helm-basename abs) abs) - collect (cond ((eq t type) - (cons (propertize disp 'face 'helm-ff-directory) - abs)) - ((stringp type) - (cons (propertize disp 'face 'helm-ff-symlink) - abs)) - (t (cons (propertize disp 'face 'helm-ff-file) - abs)))))) - -(defun helm-find--build-cmd-line () - (require 'find-cmd) - (let* ((default-directory (or (file-remote-p default-directory 'localname) - default-directory)) - (patterns+options (split-string helm-pattern "\\(\\`\\| +\\)\\* +")) - (fold-case (helm-set-case-fold-search (car patterns+options))) - (patterns (split-string (car patterns+options))) - (additional-options (and (cdr patterns+options) - (list (concat (cadr patterns+options) " ")))) - (ignored-dirs ()) - (ignored-files (when helm-findutils-skip-boring-files - (cl-loop for f in completion-ignored-extensions - if (string-match "/$" f) - do (push (replace-match "" nil t f) - ignored-dirs) - else collect (concat "*" f)))) - (path-or-name (if helm-findutils-search-full-path - '(ipath path) '(iname name))) - (name-or-iname (if fold-case - (car path-or-name) (cadr path-or-name)))) - (find-cmd (and ignored-dirs - `(prune (name ,@ignored-dirs))) - (and ignored-files - `(not (name ,@ignored-files))) - `(and ,@(mapcar - (lambda (pattern) - `(,name-or-iname ,(concat "*" pattern "*"))) - patterns) - ,@additional-options)))) - -(defun helm-find-shell-command-fn () - "Asynchronously fetch candidates for `helm-find'. -Additional find options can be specified after a \"*\" -separator." - (let* (process-connection-type - non-essential - (cmd (concat (helm-find--build-cmd-line) - (if helm-find-noerrors "2> /dev/null" ""))) - (proc (start-file-process-shell-command "hfind" helm-buffer cmd))) - (helm-log "Find command:\n%s" cmd) - (prog1 proc - (set-process-sentinel - proc - (lambda (process event) - (helm-process-deferred-sentinel-hook - process event (helm-default-directory)) - (if (string= event "finished\n") - (helm-locate-update-mode-line "Find") - (helm-log "Error: Find %s" - (replace-regexp-in-string "\n" "" event)))))))) - -(defun helm-find-1 (dir) - (let ((default-directory (file-name-as-directory dir))) - (helm :sources 'helm-source-findutils - :buffer "*helm find*" - :ff-transformer-show-only-basename nil - :case-fold-search helm-file-name-case-fold-search))) - - -;;; Preconfigured commands -;; -;; -;;;###autoload -(defun helm-find (arg) - "Preconfigured `helm' for the find shell command. - -Recursively find files whose names are matched by all specified -globbing PATTERNs under the current directory using the external -program specified in `find-program' (usually \"find\"). Every -input PATTERN is silently wrapped into two stars: *PATTERN*. - -With prefix argument, prompt for a directory to search. - -When user option `helm-findutils-search-full-path' is non-nil, -match against complete paths, otherwise, against file names -without directory part. - -The (possibly empty) list of globbing PATTERNs can be followed by -the separator \"*\" plus any number of additional arguments that -are passed to \"find\" literally." - (interactive "P") - (let ((directory - (if arg - (file-name-as-directory - (read-directory-name "DefaultDirectory: ")) - default-directory))) - (helm-find-1 directory))) - -(provide 'helm-find) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-find.el ends here diff --git a/elpa/helm-20191031.725/helm-font.el b/elpa/helm-20191031.725/helm-font.el deleted file mode 100644 index d0a37a4a..00000000 --- a/elpa/helm-20191031.725/helm-font.el +++ /dev/null @@ -1,335 +0,0 @@ -;;; helm-font --- Font and ucs selection for Helm -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'cl-lib) -(require 'helm) -(require 'helm-help) - - -(defgroup helm-font nil - "Related applications to display fonts in helm." - :group 'helm) - -(defcustom helm-ucs-recent-size 10 - "Number of recent chars to keep." - :type 'integer - :group 'helm-font) - -(defcustom helm-ucs-actions - '(("Insert character" . helm-ucs-insert-char) - ("Insert character name" . helm-ucs-insert-name) - ("Insert character code in hex" . helm-ucs-insert-code) - ("Kill marked characters" . helm-ucs-kill-char) - ("Kill name" . helm-ucs-kill-name) - ("Kill code" . helm-ucs-kill-code)) - "Actions for `helm-source-ucs'." - :group 'helm-font - :type '(alist :key-type string :value-type function)) - -(defvar helm-ucs-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "") 'helm-ucs-persistent-delete) - (define-key map (kbd "") 'helm-ucs-persistent-backward) - (define-key map (kbd "") 'helm-ucs-persistent-forward) - (define-key map (kbd "C-c SPC") 'helm-ucs-persistent-insert-space) - map) - "Keymap for `helm-ucs'.") - -(defface helm-ucs-char - '((((class color) (background dark)) (:foreground "Gold"))) - "Face used to display ucs characters." - :group 'helm-font) - -;;; Xfont selection -;; -;; -(defvar helm-xfonts-cache nil) -(defvar helm-previous-font nil) -(defvar helm-source-xfonts - (helm-build-sync-source "X Fonts" - :init (lambda () - (unless helm-xfonts-cache - (setq helm-xfonts-cache - (x-list-fonts "*"))) - ;; Save current font so it can be restored in cleanup - (setq helm-previous-font (cdr (assq 'font (frame-parameters))))) - :candidates 'helm-xfonts-cache - :action '(("Copy font to kill ring" . (lambda (elm) - (kill-new elm))) - ("Set font" . (lambda (elm) - (kill-new elm) - (set-frame-font elm 'keep-size) - (message "Font copied to kill ring")))) - :cleanup (lambda () - ;; Restore previous font - (set-frame-font helm-previous-font 'keep-size)) - :persistent-action (lambda (new-font) - (set-frame-font new-font 'keep-size) - (kill-new new-font)) - :persistent-help "Preview font and copy to kill-ring")) - - -;;; 𝕌𝕔𝕤 𝕊𝕪𝕞𝕓𝕠𝕝 𝕔𝕠𝕞𝕡𝕝𝕖𝕥𝕚𝕠𝕟 -;; -;; -(defvar helm-ucs--max-len nil) -(defvar helm-ucs--names nil) -(defvar helm-ucs-history nil) -(defvar helm-ucs-recent nil - "Ring of recent `helm-ucs' selections.") - -(defun helm-calculate-ucs-alist-max-len (names) - "Calculate the length of the longest NAMES list candidate." - (cl-loop for (_n . v) in names - maximize (length (format "#x%x:" v)) into code - maximize (max 1 (string-width (format "%c" v))) into char - finally return (cons code char))) - -(defun helm-calculate-ucs-hash-table-max-len (names) - "Calculate the length of the longest NAMES hash table candidate." - (cl-loop for _n being the hash-keys of names - using (hash-values v) - maximize (length (format "#x%x:" v)) into code - maximize (max 1 (string-width (format "%c" v))) into char - finally return (cons code char))) - -(defun helm-calculate-ucs-max-len () - "Calculate the length of longest `ucs-names' candidate." - (let ((ucs-struct (ucs-names))) - (if (hash-table-p ucs-struct) - (helm-calculate-ucs-hash-table-max-len ucs-struct) - (helm-calculate-ucs-alist-max-len ucs-struct)))) - -(defun helm-ucs-collect-symbols-alist (names) - "Collect ucs symbols from the NAMES list." - (cl-loop with pr = (make-progress-reporter - "collecting ucs names" - 0 (length names)) - for (n . v) in names - for count from 1 - for xcode = (format "#x%x:" v) - for len = (length xcode) - for diff = (- (car helm-ucs--max-len) len) - for code = (format "(#x%x): " v) - for char = (propertize (format "%c" v) - 'face 'helm-ucs-char) - unless (or (string= "" n) - ;; `char-displayable-p' return a font object or - ;; t for some char that are displayable but have - ;; no special font (e.g 10) so filter out char - ;; with no font. - (not (fontp (char-displayable-p (read xcode))))) - collect - (concat code (make-string diff ? ) - char " " n) - and do (progress-reporter-update pr count))) - -(defun helm-ucs-collect-symbols-hash-table (names) - "Collect ucs symbols from the NAMES hash-table." - (cl-loop with pr = (make-progress-reporter - "collecting ucs names" - 0 (hash-table-count names)) - for n being the hash-keys of names - using (hash-values v) - for count from 1 - for xcode = (format "#x%x:" v) - for len = (length xcode) - for diff = (- (car helm-ucs--max-len) len) - for code = (format "(#x%x): " v) - for char = (propertize (format "%c" v) - 'face 'helm-ucs-char) - unless (or (string= "" n) - (not (fontp (char-displayable-p (read xcode))))) - collect - (concat code (make-string diff ? ) - char " " n) - and do (progress-reporter-update pr count))) - -(defun helm-ucs-collect-symbols (ucs-struct) - "Collect ucs symbols from UCS-STRUCT. - -Depending on the Emacs version, the variable `ucs-names' can -either be an alist or a hash-table." - (if (hash-table-p ucs-struct) - (helm-ucs-collect-symbols-hash-table ucs-struct) - (helm-ucs-collect-symbols-alist ucs-struct))) - -(defun helm-ucs-init () - "Initialize an helm buffer with ucs symbols. -Only math* symbols are collected." - (unless helm-ucs--max-len - (setq helm-ucs--max-len - (helm-calculate-ucs-max-len))) - (or helm-ucs--names - (setq helm-ucs--names - (helm-ucs-collect-symbols (ucs-names))))) - -;; Actions (insertion) - -(defun helm-ucs-match (candidate n) - "Return the N part of an ucs CANDIDATE. -Where N=1 is the ucs code, N=2 the ucs char and N=3 the ucs name." - (when (string-match - "^(\\(#x[a-f0-9]+\\)): *\\(.\\) *\\([^:]+\\)+" - candidate) - (match-string n candidate))) - -(defun helm-ucs-save-recentest (candidate) - (let ((lst (cons candidate (delete candidate helm-ucs-recent)))) - (setq helm-ucs-recent - (if (> (length lst) helm-ucs-recent-size) - (nbutlast lst 1) - lst)))) - -(defun helm-ucs-insert (candidate n) - "Insert the N part of CANDIDATE." - (with-helm-current-buffer - (helm-ucs-save-recentest candidate) - (insert (helm-ucs-match candidate n)))) - -(defun helm-ucs-insert-char (candidate) - "Insert ucs char part of CANDIDATE at point." - (helm-ucs-insert candidate 2)) - -(defun helm-ucs-insert-code (candidate) - "Insert ucs code part of CANDIDATE at point." - (helm-ucs-insert candidate 1)) - -(defun helm-ucs-insert-name (candidate) - "Insert ucs name part of CANDIDATE at point." - (helm-ucs-insert candidate 3)) - -;; Kill actions -(defun helm-ucs-kill-char (_candidate) - "Action that concatenate ucs marked chars." - (let ((marked (helm-marked-candidates))) - (cl-loop for candidate in marked - do (helm-ucs-save-recentest candidate)) - (kill-new (mapconcat (lambda (x) - (helm-ucs-match x 2)) - marked "")))) - -(defun helm-ucs-kill-code (candidate) - (helm-ucs-save-recentest candidate) - (kill-new (helm-ucs-match candidate 1))) - -(defun helm-ucs-kill-name (candidate) - (helm-ucs-save-recentest candidate) - (kill-new (helm-ucs-match candidate 3))) - -;; Navigation in current-buffer (persistent) - -(defun helm-ucs-forward-char (_candidate) - (with-helm-current-buffer - (forward-char 1))) - -(defun helm-ucs-backward-char (_candidate) - (with-helm-current-buffer - (forward-char -1))) - -(defun helm-ucs-delete-backward (_candidate) - (with-helm-current-buffer - (delete-char -1))) - -(defun helm-ucs-insert-space (_candidate) - (with-helm-current-buffer - (insert " "))) - -(defun helm-ucs-persistent-forward () - (interactive) - (with-helm-alive-p - (helm-attrset 'action-forward 'helm-ucs-forward-char) - (helm-execute-persistent-action 'action-forward))) -(put 'helm-ucs-persistent-forward 'helm-only t) - -(defun helm-ucs-persistent-backward () - (interactive) - (with-helm-alive-p - (helm-attrset 'action-back 'helm-ucs-backward-char) - (helm-execute-persistent-action 'action-back))) -(put 'helm-ucs-persistent-backward 'helm-only t) - -(defun helm-ucs-persistent-delete () - (interactive) - (with-helm-alive-p - (helm-attrset 'action-delete 'helm-ucs-delete-backward) - (helm-execute-persistent-action 'action-delete))) -(put 'helm-ucs-persistent-delete 'helm-only t) - -(defun helm-ucs-persistent-insert-space () - (interactive) - (with-helm-alive-p - (helm-attrset 'action-insert-space 'helm-ucs-insert-space) - (helm-execute-persistent-action 'action-insert-space))) - -(defvar helm-source-ucs-recent - (helm-build-sync-source "Recent UCS" - :action helm-ucs-actions - :candidates (lambda () helm-ucs-recent) - :help-message helm-ucs-help-message - :keymap helm-ucs-map - :volatile t)) - -(defvar helm-source-ucs - (helm-build-in-buffer-source "UCS names" - :data #'helm-ucs-init - :get-line #'buffer-substring - :help-message 'helm-ucs-help-message - :filtered-candidate-transformer - (lambda (candidates _source) (sort candidates #'helm-generic-sort-fn)) - :action helm-ucs-actions - :persistent-action (lambda (candidate) - (helm-ucs-insert-char candidate) - (helm-force-update)) - :keymap helm-ucs-map) - "Source for collecting `ucs-names' math symbols.") - -;;;###autoload -(defun helm-select-xfont () - "Preconfigured `helm' to select Xfont." - (interactive) - (helm :sources 'helm-source-xfonts - :buffer "*helm select xfont*")) - -;;;###autoload -(defun helm-ucs (arg) - "Preconfigured helm for `ucs-names'. - -Called with a prefix arg force reloading cache." - (interactive "P") - (when arg - (setq helm-ucs--names nil - helm-ucs--max-len nil - ucs-names nil)) - (let ((char (helm-aif (char-after) (string it)))) - (helm :sources (list helm-source-ucs-recent helm-source-ucs) - :history 'helm-ucs-history - :input (and char (multibyte-string-p char) char) - :buffer "*helm ucs*"))) - -(provide 'helm-font) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-font.el ends here diff --git a/elpa/helm-20191031.725/helm-for-files.el b/elpa/helm-20191031.725/helm-for-files.el deleted file mode 100644 index e875c56e..00000000 --- a/elpa/helm-20191031.725/helm-for-files.el +++ /dev/null @@ -1,308 +0,0 @@ -;;; helm-for-files.el --- helm-for-files and related. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'helm-files) -(require 'helm-external) -(require 'helm-bookmark) - -(defcustom helm-multi-files-toggle-locate-binding "C-c p" - "Default binding to switch back and forth locate in `helm-multi-files'." - :group 'helm-files - :type 'string) - -(defcustom helm-for-files-preferred-list - '(helm-source-buffers-list - helm-source-recentf - helm-source-bookmarks - helm-source-file-cache - helm-source-files-in-current-dir - helm-source-locate) - "Your preferred sources for `helm-for-files' and `helm-multi-files'. - -When adding a source here it is up to you to ensure the library of -this source is accessible and properly loaded." - :type '(repeat (choice symbol)) - :group 'helm-files) - -(defcustom helm-for-files-tramp-not-fancy t - "Colorize remote files when non nil. - -Be aware that a nil value will make tramp display very slow." - :group 'helm-files - :type 'boolean) - -;;; File Cache -;; -;; -(defvar file-cache-alist) - -(defclass helm-file-cache (helm-source-in-buffer helm-type-file) - ((init :initform (lambda () (require 'filecache))))) - -(defun helm-file-cache-get-candidates () - (cl-loop for item in file-cache-alist append - (cl-destructuring-bind (base &rest dirs) item - (cl-loop for dir in dirs collect - (concat dir base))))) - -(defvar helm-source-file-cache nil) - -(defcustom helm-file-cache-fuzzy-match nil - "Enable fuzzy matching in `helm-source-file-cache' when non--nil." - :group 'helm-files - :type 'boolean - :set (lambda (var val) - (set var val) - (setq helm-source-file-cache - (helm-make-source "File Cache" 'helm-file-cache - :fuzzy-match helm-file-cache-fuzzy-match - :data 'helm-file-cache-get-candidates)))) - -(cl-defun helm-file-cache-add-directory-recursively - (dir &optional match (ignore-dirs t)) - (require 'filecache) - (cl-loop for f in (helm-walk-directory - dir - :path 'full - :directories nil - :match match - :skip-subdirs ignore-dirs) - do (file-cache-add-file f))) - -(defun helm-transform-file-cache (actions _candidate) - (let ((source (helm-get-current-source))) - (if (string= (assoc-default 'name source) "File Cache") - (append actions - '(("Remove marked files from file-cache" - . helm-ff-file-cache-remove-file))) - actions))) - -;;; Recentf files -;; -;; -(defvar helm-recentf--basename-flag nil) - -(defun helm-recentf-pattern-transformer (pattern) - (let ((pattern-no-flag (replace-regexp-in-string " -b" "" pattern))) - (cond ((and (string-match " " pattern-no-flag) - (string-match " -b\\'" pattern)) - (setq helm-recentf--basename-flag t) - pattern-no-flag) - ((string-match "\\([^ ]*\\) -b\\'" pattern) - (prog1 (match-string 1 pattern) - (setq helm-recentf--basename-flag t))) - (t (setq helm-recentf--basename-flag nil) - pattern)))) - -(defcustom helm-turn-on-recentf t - "Automatically turn on `recentf-mode' when non-nil." - :group 'helm-files - :type 'boolean) - -(defclass helm-recentf-source (helm-source-sync helm-type-file) - ((init :initform (lambda () - (require 'recentf) - (when helm-turn-on-recentf (recentf-mode 1)))) - (candidates :initform (lambda () recentf-list)) - (pattern-transformer :initform 'helm-recentf-pattern-transformer) - (match-part :initform (lambda (candidate) - (if (or helm-ff-transformer-show-only-basename - helm-recentf--basename-flag) - (helm-basename candidate) candidate))) - (migemo :initform t) - (persistent-action :initform 'helm-ff-kill-or-find-buffer-fname))) - -(defmethod helm--setup-source :after ((source helm-recentf-source)) - (setf (slot-value source 'action) - (append (symbol-value (helm-actions-from-type-file)) - '(("Delete file(s) from recentf" . - (lambda (_candidate) - (cl-loop for file in (helm-marked-candidates) - do (setq recentf-list (delete file recentf-list))))))))) - -(defvar helm-source-recentf nil - "See (info \"(emacs)File Conveniences\"). -Set `recentf-max-saved-items' to a bigger value if default is too small.") - -(defcustom helm-recentf-fuzzy-match nil - "Enable fuzzy matching in `helm-source-recentf' when non--nil." - :group 'helm-files - :type 'boolean - :set (lambda (var val) - (set var val) - (let ((helm-fuzzy-sort-fn 'helm-fuzzy-matching-sort-fn-preserve-ties-order)) - (setq helm-source-recentf - (helm-make-source "Recentf" 'helm-recentf-source - :fuzzy-match helm-recentf-fuzzy-match))))) - - -;;; Files in current dir -;; -;; -(defun helm-highlight-files (files _source) - "A basic transformer for helm files sources. -Colorize only symlinks, directories and files." - (cl-loop with mp-fn = (or (assoc-default - 'match-part (helm-get-current-source)) - 'identity) - for i in files - for disp = (if (and helm-ff-transformer-show-only-basename - (not (helm-dir-is-dot i)) - (not (and helm--url-regexp - (string-match helm--url-regexp i))) - (not (string-match helm-ff-url-regexp i))) - (helm-basename i) (abbreviate-file-name i)) - for isremote = (or (file-remote-p i) - (helm-file-on-mounted-network-p i)) - ;; Call file-attributes only if: - ;; - file is not remote - ;; - helm-for-files--tramp-not-fancy is nil and file is remote AND - ;; connected. (Issue #1679) - for type = (and (or (null isremote) - (and (null helm-for-files-tramp-not-fancy) - (file-remote-p i nil t))) - (car (file-attributes i))) - collect - (cond ((and (null type) isremote) (cons disp i)) - ((stringp type) - (cons (propertize disp - 'face 'helm-ff-symlink - 'match-part (funcall mp-fn disp) - 'help-echo (expand-file-name i)) - i)) - ((eq type t) - (cons (propertize disp - 'face 'helm-ff-directory - 'match-part (funcall mp-fn disp) - 'help-echo (expand-file-name i)) - i)) - (t (cons (propertize disp - 'face 'helm-ff-file - 'match-part (funcall mp-fn disp) - 'help-echo (expand-file-name i)) - i))))) - -(defclass helm-files-in-current-dir-source (helm-source-sync helm-type-file) - ((candidates :initform (lambda () - (with-helm-current-buffer - (let ((dir (helm-current-directory))) - (when (file-accessible-directory-p dir) - (directory-files dir t)))))) - (pattern-transformer :initform 'helm-recentf-pattern-transformer) - (match-part :initform (lambda (candidate) - (if (or helm-ff-transformer-show-only-basename - helm-recentf--basename-flag) - (helm-basename candidate) candidate))) - (fuzzy-match :initform t) - (migemo :initform t))) - -(defvar helm-source-files-in-current-dir - (helm-make-source "Files from Current Directory" - 'helm-files-in-current-dir-source)) - -;;;###autoload -(defun helm-for-files () - "Preconfigured `helm' for opening files. -Run all sources defined in `helm-for-files-preferred-list'." - (interactive) - (require 'helm-x-files) - (unless helm-source-buffers-list - (setq helm-source-buffers-list - (helm-make-source "Buffers" 'helm-source-buffers))) - (helm :sources helm-for-files-preferred-list - :ff-transformer-show-only-basename nil - :buffer "*helm for files*" - :truncate-lines helm-buffers-truncate-lines)) - -(defun helm-multi-files-toggle-to-locate () - (interactive) - (with-helm-alive-p - (with-helm-buffer - (if (setq helm-multi-files--toggle-locate - (not helm-multi-files--toggle-locate)) - (progn - (helm-set-sources (unless (memq 'helm-source-locate - helm-sources) - (cons 'helm-source-locate helm-sources))) - (helm-set-source-filter '(helm-source-locate))) - (helm-kill-async-processes) - (helm-set-sources (remove 'helm-source-locate - helm-for-files-preferred-list)) - (helm-set-source-filter nil))))) -(put 'helm-multi-files-toggle-to-locate 'helm-only t) - -;;;###autoload -(defun helm-multi-files () - "Preconfigured helm like `helm-for-files' but running locate only on demand. - -Allow toggling back and forth from locate to others sources with -`helm-multi-files-toggle-locate-binding' key. -This avoid launching needlessly locate when what you search is already -found." - (interactive) - (require 'helm-x-files) - (unless helm-source-buffers-list - (setq helm-source-buffers-list - (helm-make-source "Buffers" 'helm-source-buffers))) - (setq helm-multi-files--toggle-locate nil) - (helm-locate-set-command) - (helm-set-local-variable 'helm-async-outer-limit-hook - (list (lambda () - (when (and helm-locate-fuzzy-match - (not (string-match-p - "\\s-" helm-pattern))) - (helm-redisplay-buffer))))) - (let ((sources (remove 'helm-source-locate helm-for-files-preferred-list)) - (helm-locate-command - (if helm-locate-fuzzy-match - (unless (string-match-p "\\`locate -b" helm-locate-command) - (replace-regexp-in-string - "\\`locate" "locate -b" helm-locate-command)) - helm-locate-command)) - (old-key (lookup-key - helm-map - (read-kbd-macro helm-multi-files-toggle-locate-binding)))) - (with-helm-temp-hook 'helm-after-initialize-hook - (define-key helm-map (kbd helm-multi-files-toggle-locate-binding) - 'helm-multi-files-toggle-to-locate)) - (unwind-protect - (helm :sources sources - :ff-transformer-show-only-basename nil - :buffer "*helm multi files*" - :truncate-lines helm-buffers-truncate-lines) - (define-key helm-map (kbd helm-multi-files-toggle-locate-binding) - old-key)))) - -;;;###autoload -(defun helm-recentf () - "Preconfigured `helm' for `recentf'." - (interactive) - (helm :sources 'helm-source-recentf - :ff-transformer-show-only-basename nil - :buffer "*helm recentf*")) - -(provide 'helm-for-files) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-for-files.el ends here diff --git a/elpa/helm-20191031.725/helm-grep.el b/elpa/helm-20191031.725/helm-grep.el deleted file mode 100644 index 43b491e3..00000000 --- a/elpa/helm-20191031.725/helm-grep.el +++ /dev/null @@ -1,1661 +0,0 @@ -;;; helm-grep.el --- Helm Incremental Grep. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: -(require 'cl-lib) -(require 'format-spec) -(require 'helm) -(require 'helm-help) -(require 'helm-regexp) - -;;; load wgrep proxy if it's available -(require 'wgrep-helm nil t) - -(declare-function helm-buffer-list "helm-buffers") -(declare-function View-quit "view") -(declare-function doc-view-goto-page "doc-view" (page)) -(declare-function pdf-view-goto-page "pdf-view" (page &optional window)) -(declare-function helm-mm-split-pattern "helm-multi-match") -(declare-function helm--ansi-color-apply "helm-lib") -(defvar helm--ansi-color-regexp) - - -(defgroup helm-grep nil - "Grep related Applications and libraries for Helm." - :group 'helm) - -(defcustom helm-grep-default-command - "grep --color=always -a -d skip %e -n%cH -e %p %f" - "Default grep format command for `helm-do-grep-1'. -Where: -'%e' format spec is for --exclude or --include grep options or - ack-grep --type option. (Not mandatory) - -'%c' format spec is for case-fold-search, - whether to use the -i option of grep. (Not mandatory) - When you specify this spec, helm grep will use smartcase - that is when a upcase character is found in pattern case will - be respected and no '-i' option will be used, otherwise, when - no upcase character is found in pattern always use '-i'. - If you don't want this behavior, don't use this spec and - specify or not the '-i' option. - Note that with ack-grep this is not needed, just specify - the '--smart-case' option. - -'%p' format spec is for pattern. (Mandatory) - -'%f' format spec is for filenames. (Mandatory) - -If your grep version doesn't support the --exclude/include args -don't specify the '%e' format spec. - -Helm also support ack-grep and git-grep , -here a default command example for ack-grep: - -\(setq helm-grep-default-command \"ack-grep -Hn --color --smart-case --no-group %e %p %f\" - helm-grep-default-recurse-command \"ack-grep -H --color --smart-case --no-group %e %p %f\") - -You can ommit the %e spec if you don't want to be prompted for types. - -NOTE: Helm for ack-grep support ANSI sequences, so you can remove -the \"--no-color\" option safely (recommended) -However you should specify --color to enable multi matches highlighting -because ack disable it when output is piped. - -Same for grep you can use safely the option \"--color=always\" (default). -You can customize the color of matches using GREP_COLORS env var. -e.g: \(setenv \"GREP_COLORS\" \"ms=30;43:mc=30;43:sl=01;37:cx=:fn=35:ln=32:bn=32:se=36\") - -To enable ANSI color in git-grep just add \"--color=always\". -To customize the ANSI color in git-grep, GREP_COLORS have no effect, -you will have to setup this in your .gitconfig: - - [color \"grep\"] - match = black yellow - -where \"black\" is the foreground and \"yellow\" the background. -See the git documentation for more infos. - -`helm-grep-default-command' and `helm-grep-default-recurse-command'are -independents, so you can enable `helm-grep-default-command' with ack-grep -and `helm-grep-default-recurse-command' with grep if you want to be faster -on recursive grep. - -NOTE: Remote grepping is not available with ack-grep, - and badly supported with grep because tramp handle badly - repeated remote processes in a short delay (< to 5s)." - :group 'helm-grep - :type 'string) - -(defcustom helm-grep-default-recurse-command - "grep --color=always -a -d recurse %e -n%cH -e %p %f" - "Default recursive grep format command for `helm-do-grep-1'. -See `helm-grep-default-command' for format specs and infos about ack-grep." - :group 'helm-grep - :type 'string) - -(defcustom helm-default-zgrep-command - "zgrep --color=always -a -n%cH -e %p %f" - "Default command for Zgrep. -See `helm-grep-default-command' for infos on format specs. -Option --color=always is supported and can be used safely -to replace the helm internal match highlighting, -see `helm-grep-default-command' for more infos." - :group 'helm-grep - :type 'string) - -(defcustom helm-pdfgrep-default-command - "pdfgrep --color always -niH %s %s" - "Default command for pdfgrep. -Option \"--color always\" is supported starting helm version 1.7.8, -when used matchs will be highlighted according to GREP_COLORS env var." - :group 'helm-grep - :type 'string) - -(defcustom helm-pdfgrep-default-recurse-command - "pdfgrep --color always -rniH %s %s" - "Default recurse command for pdfgrep. -Option \"--color always\" is supported starting helm version 1.7.8, -when used matchs will be highlighted according to GREP_COLORS env var." - :group 'helm-grep - :type 'string) - -(defcustom helm-pdfgrep-default-read-command nil - "Default command to read pdf files from pdfgrep. -Where '%f' format spec is filename and '%p' is page number. -e.g In Ubuntu you can set it to: - - \"evince --page-label=%p '%f'\" - -If set to nil either `doc-view-mode' or `pdf-view-mode' will be used -instead of an external command." - :group 'helm-grep - :type 'string) - -(defcustom helm-grep-max-length-history 100 - "Max number of elements to save in `helm-grep-history'." - :group 'helm-grep - :type 'integer) - -(defcustom helm-zgrep-file-extension-regexp - ".*\\(\\.gz\\|\\.bz\\|\\.xz\\|\\.lzma\\)$" - "Default file extensions zgrep will search in." - :group 'helm-grep - :type 'string) - -(defcustom helm-grep-preferred-ext nil - "This file extension will be preselected for grep." - :group 'helm-grep - :type 'string) - -(defcustom helm-grep-save-buffer-name-no-confirm nil - "when *hgrep* already exists,auto append suffix." - :group 'helm-grep - :type 'boolean) - -(defcustom helm-grep-ignored-files - (cons ".#*" (delq nil (mapcar (lambda (s) - (unless (string-match-p "/\\'" s) - (concat "*" s))) - completion-ignored-extensions))) - "List of file names which `helm-grep' shall exclude." - :group 'helm-grep - :type '(repeat string)) - -(defcustom helm-grep-ignored-directories - helm-walk-ignore-directories - "List of names of sub-directories which `helm-grep' shall not recurse into." - :group 'helm-grep - :type '(repeat string)) - -(defcustom helm-grep-truncate-lines t - "When nil the grep line that appears will not be truncated." - :group 'helm-grep - :type 'boolean) - -(defcustom helm-grep-file-path-style 'basename - "File path display style when grep results are displayed. -Possible value are: - basename: displays only the filename, none of the directory path - absolute: displays absolute path - relative: displays relative path from root grep directory." - :group 'helm-grep - :type '(choice (const :tag "Basename" basename) - (const :tag "Absolute" absolute) - (const :tag "Relative" relative))) - -(defcustom helm-grep-actions - (helm-make-actions - "Find File" 'helm-grep-action - "Find file other frame" 'helm-grep-other-frame - "Save results in grep buffer" 'helm-grep-save-results - "Find file other window (C-u vertically)" 'helm-grep-other-window) - "Actions for helm grep." - :group 'helm-grep - :type '(alist :key-type string :value-type function)) - -(defcustom helm-grep-pipe-cmd-switches nil - "A list of additional parameters to pass to grep pipe command. -This will be used for pipe command for multiple pattern matching -for grep, zgrep ack-grep and git-grep backends. -If you add extra args for ack-grep, use ack-grep options, -for others (grep, zgrep and git-grep) use grep options. -Here are the commands where you may want to add switches: - - grep --color=always - ack-grep --smart-case --color - -You probably don't need to use this unless you know what you are doing." - :group 'helm-grep - :type '(repeat string)) - -(defcustom helm-grep-ag-pipe-cmd-switches nil - "A list of additional parameters to pass to grep-ag pipe command. -Use parameters compatibles with the backend you are using -\(i.e AG for AG, PT for PT or RG for RG) - -You probably don't need to use this unless you know what you are doing." - :group 'helm-grep - :type '(repeat string)) - -(defcustom helm-grep-input-idle-delay 0.6 - "Same as `helm-input-idle-delay' but for grep commands. -It have a higher value than `helm-input-idle-delay' to avoid -flickering when updating." - :group 'helm-grep - :type 'float) - -;;; Faces -;; -;; -(defgroup helm-grep-faces nil - "Customize the appearance of helm-grep." - :prefix "helm-" - :group 'helm-grep - :group 'helm-faces) - -(defface helm-grep-match - '((((background light)) :foreground "#b00000") - (((background dark)) :foreground "gold1")) - "Face used to highlight grep matches. -Have no effect when grep backend use \"--color=\"." - :group 'helm-grep-faces) - -(defface helm-grep-file - '((t (:foreground "BlueViolet" - :underline t))) - "Face used to highlight grep results filenames." - :group 'helm-grep-faces) - -(defface helm-grep-lineno - '((t (:foreground "Darkorange1"))) - "Face used to highlight grep number lines." - :group 'helm-grep-faces) - -(defface helm-grep-finish - '((t (:foreground "Green"))) - "Face used in mode line when grep is finish." - :group 'helm-grep-faces) - -(defface helm-grep-cmd-line - '((t (:inherit font-lock-type-face))) - "Face used to highlight grep command line when no results." - :group 'helm-grep-faces) - - -;;; Keymaps -;; -;; -(defvar helm-grep-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "M-") 'helm-goto-next-file) - (define-key map (kbd "M-") 'helm-goto-precedent-file) - (define-key map (kbd "C-c o") 'helm-grep-run-other-window-action) - (define-key map (kbd "C-c C-o") 'helm-grep-run-other-frame-action) - (define-key map (kbd "C-x C-s") 'helm-grep-run-save-buffer) - (define-key map (kbd "DEL") 'helm-delete-backward-no-update) - map) - "Keymap used in Grep sources.") - -(defcustom helm-grep-use-ioccur-style-keys t - "Use Arrow keys to jump to occurences. -Note that if you define this variable with `setq' your change will -have no effect, use customize instead." - :group 'helm-grep - :type 'boolean - :set (lambda (var val) - (set var val) - (if val - (progn - (define-key helm-grep-map (kbd "") 'helm-execute-persistent-action) - (define-key helm-grep-map (kbd "") 'helm-grep-run-default-action)) - (define-key helm-grep-map (kbd "") nil) - (define-key helm-grep-map (kbd "") nil)))) - -(defvar helm-pdfgrep-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "M-") 'helm-goto-next-file) - (define-key map (kbd "M-") 'helm-goto-precedent-file) - (define-key map (kbd "DEL") 'helm-delete-backward-no-update) - map) - "Keymap used in pdfgrep.") - -(defvar helm-grep-mode-map - (let ((map (make-sparse-keymap))) - (define-key map (kbd "RET") 'helm-grep-mode-jump) - (define-key map (kbd "C-o") 'helm-grep-mode-jump-other-window) - (define-key map (kbd "") 'helm-grep-mode-jump-other-window-forward) - (define-key map (kbd "") 'helm-grep-mode-jump-other-window-backward) - (define-key map (kbd "") 'helm-gm-next-file) - (define-key map (kbd "") 'helm-gm-precedent-file) - (define-key map (kbd "M-n") 'helm-grep-mode-jump-other-window-forward) - (define-key map (kbd "M-p") 'helm-grep-mode-jump-other-window-backward) - (define-key map (kbd "M-N") 'helm-gm-next-file) - (define-key map (kbd "M-P") 'helm-gm-precedent-file) - map)) - - -;;; Internals vars -;; -;; -(defvar helm-rzgrep-cache (make-hash-table :test 'equal)) -(defvar helm-grep-default-function 'helm-grep-init) -(defvar helm-zgrep-recurse-flag nil) -(defvar helm-grep-history nil) -(defvar helm-grep-ag-history nil) -(defvar helm-grep-last-targets nil) -(defvar helm-grep-include-files nil) -(defvar helm-grep-in-recurse nil) -(defvar helm-grep-use-zgrep nil) -(defvar helm-grep-default-directory-fn nil - "A function that should return a directory to expand candidate to. -It is intended to use as a let-bound variable, DON'T set this globaly.") -(defvar helm-pdfgrep-targets nil) -(defvar helm-grep-last-cmd-line nil) -(defvar helm-grep-split-line-regexp "^\\([[:lower:][:upper:]]?:?.*?\\):\\([0-9]+\\):\\(.*\\)") - - -;;; Init -;; -;; -(defun helm-grep-prepare-candidates (candidates in-directory) - "Prepare filenames and directories CANDIDATES for grep command line." - ;; If one or more candidate is a directory, search in all files - ;; of this candidate (e.g /home/user/directory/*). - ;; If r option is enabled search also in subdidrectories. - ;; We need here to expand wildcards to support crap windows filenames - ;; as grep doesn't accept quoted wildcards (e.g "dir/*.el"). - (if helm-zgrep-recurse-flag - (mapconcat 'shell-quote-argument candidates " ") - ;; When candidate is a directory, search in all its files. - ;; NOTE that `file-expand-wildcards' will return also - ;; directories, they will be ignored by grep but not - ;; by ack-grep that will grep all files of this directory - ;; without recursing in their subdirs though, see that as a one - ;; level recursion with ack-grep. - ;; So I leave it as it is, considering it is a feature. [1] - (cl-loop for i in candidates append - (cond ((string-match "^git" helm-grep-default-command) - (list i)) - ;; Candidate is a directory and we use recursion or ack. - ((and (file-directory-p i) - (or helm-grep-in-recurse - ;; ack-grep accept directory [1]. - (helm-grep-use-ack-p))) - (list (expand-file-name i))) - ;; Grep doesn't support directory only when not in recurse. - ((file-directory-p i) - (file-expand-wildcards - (concat (file-name-as-directory (expand-file-name i)) "*") t)) - ;; Candidate is a file or wildcard and we use recursion, use the - ;; current directory instead of candidate. - ((and (or (file-exists-p i) (string-match "[*]" i)) - helm-grep-in-recurse) - (list (expand-file-name - (directory-file-name ; Needed for windoze. - (file-name-directory (directory-file-name i)))))) - ;; Else should be one or more file/directory - ;; possibly marked. - ;; When real is a normal filename without wildcard - ;; file-expand-wildcards returns a list of one file. - ;; wildcards should have been already handled by - ;; helm-read-file-name or helm-find-files but do it from - ;; here too in case we are called from elsewhere. - (t (file-expand-wildcards i t))) into all-files ; [1] - finally return - (let ((files (if (file-remote-p in-directory) - ;; Grep don't understand tramp filenames - ;; use the local name. - (mapcar (lambda (x) - (file-remote-p x 'localname)) - all-files) - all-files))) - ;; When user mark files and use recursion with grep - ;; backend enabled, the loop collect on each marked - ;; candidate its `file-name-directory' and we endup with - ;; duplicates (Issue #1714). FIXME: For now as a quick fix - ;; I just remove dups here but I should handle this inside - ;; the cond above. - (setq files (helm-fast-remove-dups files :test 'equal)) - (if (string-match "^git" helm-grep-default-command) - (mapconcat 'identity files " ") - (mapconcat 'shell-quote-argument files " ")))))) - -(defun helm-grep-command (&optional recursive grep) - (let* ((com (if recursive - helm-grep-default-recurse-command - helm-grep-default-command)) - (exe (if grep - (symbol-name grep) - (and com (car (split-string com " ")))))) - (if (and exe (string= exe "git")) "git-grep" exe))) - -(cl-defun helm-grep-use-ack-p (&key where) - (let* ((rec-com (helm-grep-command t)) - (norm-com (helm-grep-command)) - (norm-com-ack-p (string-match "\\`ack" norm-com)) - (rec-com-ack-p (and rec-com (string-match "\\`ack" rec-com)))) - (cl-case where - (default (and norm-com norm-com-ack-p)) - (recursive (and rec-com rec-com-ack-p)) - (strict (and norm-com rec-com rec-com-ack-p norm-com-ack-p)) - (t (and (not (and norm-com (string= norm-com "git-grep"))) - (or (and norm-com norm-com-ack-p) - (and rec-com rec-com-ack-p))))))) - -(defun helm-grep--pipe-command-for-grep-command (smartcase pipe-switches &optional grep-cmd) - (pcase (or grep-cmd (helm-grep-command)) - ;; Use grep for GNU regexp based tools. - ((or "grep" "zgrep" "git-grep") - (format "grep --color=always%s %s" - (if smartcase " -i" "") - pipe-switches)) - ;; Use ack-grep for PCRE based tools. - ;; Sometimes ack-grep cmd is ack only. - ((and (pred (string-match-p "ack")) ack) - (format "%s --smart-case --color %s" ack pipe-switches)))) - -(defun helm-grep--prepare-cmd-line (only-files &optional include zgrep) - (let* ((default-directory (or helm-ff-default-directory - (helm-default-directory) - default-directory)) - (fnargs (helm-grep-prepare-candidates - only-files default-directory)) - (ignored-files (unless (helm-grep-use-ack-p) - (mapconcat - (lambda (x) - (concat "--exclude=" - (shell-quote-argument x))) - helm-grep-ignored-files " "))) - (ignored-dirs (unless (helm-grep-use-ack-p) - (mapconcat - ;; Need grep version >=2.5.4 - ;; of Gnuwin32 on windoze. - (lambda (x) - (concat "--exclude-dir=" - (shell-quote-argument x))) - helm-grep-ignored-directories " "))) - (exclude (unless (helm-grep-use-ack-p) - (if helm-grep-in-recurse - (concat (or include ignored-files) - " " ignored-dirs) - ignored-files))) - (types (and (helm-grep-use-ack-p) - ;; When %e format spec is not specified - ;; in `helm-grep-default-command' - ;; we need to pass an empty string - ;; to types to avoid error. - (or include ""))) - (smartcase (if (helm-grep-use-ack-p) - "" - (unless (let ((case-fold-search nil)) - (string-match-p - "[[:upper:]]" helm-pattern)) - "i"))) - (helm-grep-default-command - (concat helm-grep-default-command " %m")) ; `%m' like multi. - (patterns (helm-mm-split-pattern helm-pattern t)) - (pipe-switches (mapconcat 'identity helm-grep-pipe-cmd-switches " ")) - (pipes - (helm-aif (cdr patterns) - (cl-loop with pipcom = (helm-grep--pipe-command-for-grep-command - smartcase pipe-switches) - for p in it concat - (format " | %s %s" pipcom (shell-quote-argument p))) - ""))) - (format-spec - helm-grep-default-command - (delq nil - (list (unless zgrep - (if types - (cons ?e types) - (cons ?e exclude))) - (cons ?c (or smartcase "")) - (cons ?p (shell-quote-argument (car patterns))) - (cons ?f fnargs) - (cons ?m pipes)))))) - -(defun helm-grep-init (cmd-line) - "Start an asynchronous grep process with CMD-LINE using ZGREP if non--nil." - (let* ((default-directory (or helm-ff-default-directory - (helm-default-directory) - default-directory)) - (zgrep (string-match "\\`zgrep" cmd-line)) - ;; Use pipe only with grep, zgrep or git-grep. - (process-connection-type (and (not zgrep) (helm-grep-use-ack-p))) - (tramp-verbose helm-tramp-verbose) - (start-time (float-time)) - (proc-name (if helm-grep-use-zgrep - "Zgrep" - (capitalize - (if helm-grep-in-recurse - (helm-grep-command t) - (helm-grep-command))))) - non-essential) - ;; Start grep process. - (helm-log "Starting Grep process in directory `%s'" default-directory) - (helm-log "Command line used was:\n\n%s" - (concat ">>> " (propertize cmd-line 'face 'helm-grep-cmd-line) "\n\n")) - (prog1 ; This function should return the process first. - (start-file-process-shell-command - proc-name helm-buffer cmd-line) - ;; Init sentinel. - (set-process-sentinel - (get-buffer-process helm-buffer) - (lambda (process event) - (let* ((err (process-exit-status process)) - (noresult (= err 1))) - (unless (and err (> err 0)) - (helm-process-deferred-sentinel-hook - process event (helm-default-directory))) - (cond ((and noresult - ;; This is a workaround for zgrep - ;; that exit with code 1 - ;; after a certain amount of results. - (with-helm-buffer (helm-empty-buffer-p))) - (with-helm-buffer - (insert (concat "* Exit with code 1, no result found," - " command line was:\n\n " - (propertize helm-grep-last-cmd-line - 'face 'helm-grep-cmd-line))) - (setq mode-line-format - `(" " mode-line-buffer-identification " " - (:eval (format "L%s" (helm-candidate-number-at-point))) " " - (:eval (propertize - (format - "[%s process finished - (no results)] " - ,proc-name) - 'face 'helm-grep-finish)))))) - ((or (string= event "finished\n") - (and noresult - ;; This is a workaround for zgrep - ;; that exit with code 1 - ;; after a certain amount of results. - (with-helm-buffer (not (helm-empty-buffer-p))))) - (helm-log "%s process finished with %s results in %fs" - proc-name - (helm-get-candidate-number) - (- (float-time) start-time)) - (helm-maybe-show-help-echo) - (with-helm-window - (setq mode-line-format - `(" " mode-line-buffer-identification " " - (:eval (format "L%s" (helm-candidate-number-at-point))) " " - (:eval (propertize - (format - "[%s process finished in %.2fs - (%s results)] " - ,proc-name - ,(- (float-time) start-time) - (helm-get-candidate-number)) - 'face 'helm-grep-finish)))) - (force-mode-line-update) - (when (and helm-allow-mouse helm-selection-point) - (helm--bind-mouse-for-selection helm-selection-point)))) - ;; Catch error output in log. - (t (helm-log - "Error: %s %s" - proc-name - (replace-regexp-in-string "\n" "" event)))))))))) - -(defun helm-grep-collect-candidates () - (let ((cmd-line (helm-grep--prepare-cmd-line - helm-grep-last-targets - helm-grep-include-files - helm-grep-use-zgrep))) - (set (make-local-variable 'helm-grep-last-cmd-line) cmd-line) - (funcall helm-grep-default-function cmd-line))) - - -;;; Actions -;; -;; -(defun helm-grep-action (candidate &optional where) - "Define a default action for `helm-do-grep-1' on CANDIDATE. -WHERE can be one of other-window, other-frame." - (let* ((split (helm-grep-split-line candidate)) - (split-pat (helm-mm-split-pattern helm-input)) - (lineno (string-to-number (nth 1 split))) - (loc-fname (or (with-current-buffer - (if (eq major-mode 'helm-grep-mode) - (current-buffer) - helm-buffer) - (get-text-property (point-at-bol) 'helm-grep-fname)) - (car split))) - (tramp-method (file-remote-p (or helm-ff-default-directory - default-directory) 'method)) - (tramp-host (file-remote-p (or helm-ff-default-directory - default-directory) 'host)) - (tramp-prefix (concat "/" tramp-method ":" tramp-host ":")) - (fname (if tramp-host - (concat tramp-prefix loc-fname) loc-fname))) - (cl-case where - (other-window (helm-window-show-buffers - (list (find-file-noselect fname)) t)) - (other-frame (find-file-other-frame fname)) - (grep (helm-grep-save-results-1)) - (pdf (if helm-pdfgrep-default-read-command - (helm-pdfgrep-action-1 split lineno (car split)) - (find-file (car split)) (if (derived-mode-p 'pdf-view-mode) - (pdf-view-goto-page lineno) - (doc-view-goto-page lineno)))) - (t (find-file fname))) - (unless (or (eq where 'grep) (eq where 'pdf)) - (helm-goto-line lineno)) - ;; Move point to the nearest matching regexp from bol. - (cl-loop for reg in split-pat - when (save-excursion - (condition-case _err - (if helm-migemo-mode - (helm-mm-migemo-forward reg (point-at-eol) t) - (re-search-forward reg (point-at-eol) t)) - (invalid-regexp nil))) - collect (match-beginning 0) into pos-ls - finally (when pos-ls (goto-char (apply #'min pos-ls)))) - ;; Save history - (unless (or helm-in-persistent-action - (eq major-mode 'helm-grep-mode) - (string= helm-pattern "")) - (setq helm-grep-history - (cons helm-pattern - (delete helm-pattern helm-grep-history))) - (when (> (length helm-grep-history) - helm-grep-max-length-history) - (setq helm-grep-history - (delete (car (last helm-grep-history)) - helm-grep-history)))))) - -(defun helm-grep-persistent-action (candidate) - "Persistent action for `helm-do-grep-1'. -With a prefix arg record CANDIDATE in `mark-ring'." - (helm-grep-action candidate) - (helm-highlight-current-line)) - -(defun helm-grep-other-window (candidate) - "Jump to result in other window from helm grep." - (helm-grep-action candidate 'other-window)) - -(defun helm-grep-other-frame (candidate) - "Jump to result in other frame from helm grep." - (helm-grep-action candidate 'other-frame)) - -(defun helm-goto-next-or-prec-file (n) - "Go to next or precedent candidate file in helm grep/etags buffers. -If N is positive go forward otherwise go backward." - (let* ((allow-mode (or (eq major-mode 'helm-grep-mode) - (eq major-mode 'helm-moccur-mode) - (eq major-mode 'helm-occur-mode))) - (sel (if allow-mode - (buffer-substring (point-at-bol) (point-at-eol)) - (helm-get-selection nil t))) - (current-line-list (helm-grep-split-line sel)) - (current-fname (nth 0 current-line-list)) - (bob-or-eof (if (eq n 1) 'eobp 'bobp)) - (mark-maybe (lambda () - (if allow-mode - (ignore) - (helm-mark-current-line))))) - (catch 'break - (while (not (funcall bob-or-eof)) - (forward-line n) ; Go forward or backward depending of n value. - ;; Exit when current-fname is not matched or in `helm-grep-mode' - ;; the line is not a grep line i.e 'fname:num:tag'. - (setq sel (buffer-substring (point-at-bol) (point-at-eol))) - (when helm-allow-mouse - (helm--mouse-reset-selection-help-echo)) - (unless (or (string= current-fname - (car (helm-grep-split-line sel))) - (and (eq major-mode 'helm-grep-mode) - (not (get-text-property (point-at-bol) 'helm-grep-fname)))) - (funcall mark-maybe) - (throw 'break nil)))) - (cond ((and (> n 0) (eobp)) - (re-search-backward ".") - (forward-line 0) - (funcall mark-maybe)) - ((and (< n 0) (bobp)) - (helm-aif (next-single-property-change (point-at-bol) 'helm-grep-fname) - (goto-char it) - (forward-line 1)) - (funcall mark-maybe))) - (unless allow-mode - (helm-follow-execute-persistent-action-maybe) - (helm-log-run-hook 'helm-move-selection-after-hook)))) - -;;;###autoload -(defun helm-goto-precedent-file () - "Go to precedent file in helm grep/etags buffers." - (interactive) - (with-helm-alive-p - (with-helm-window - (helm-goto-next-or-prec-file -1)))) -(put 'helm-goto-precedent-file 'helm-only t) - -;;;###autoload -(defun helm-goto-next-file () - "Go to precedent file in helm grep/etags buffers." - (interactive) - (with-helm-window - (helm-goto-next-or-prec-file 1))) - -(defun helm-grep-run-default-action () - "Run grep default action from `helm-do-grep-1'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-grep-action))) -(put 'helm-grep-run-default-action 'helm-only t) - -(defun helm-grep-run-other-window-action () - "Run grep goto other window action from `helm-do-grep-1'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-grep-other-window))) -(put 'helm-grep-run-other-window-action 'helm-only t) - -(defun helm-grep-run-other-frame-action () - "Run grep goto other frame action from `helm-do-grep-1'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-grep-other-frame))) -(put 'helm-grep-run-other-frame-action 'helm-only t) - -(defun helm-grep-run-save-buffer () - "Run grep save results action from `helm-do-grep-1'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-grep-save-results))) -(put 'helm-grep-run-save-buffer 'helm-only t) - - -;;; helm-grep-mode -;; -;; -(defun helm-grep-save-results (candidate) - (helm-grep-action candidate 'grep)) - -(defun helm-grep-save-results-1 () - "Save helm grep result in a `helm-grep-mode' buffer." - (let ((buf "*hgrep*") - new-buf - (pattern (with-helm-buffer helm-input-local)) - (src-name (assoc-default 'name (helm-get-current-source)))) - (when (get-buffer buf) - (if helm-grep-save-buffer-name-no-confirm - (setq new-buf (format "*hgrep|%s|-%s" pattern - (format-time-string "%H-%M-%S*"))) - (setq new-buf (helm-read-string "GrepBufferName: " buf)) - (cl-loop for b in (helm-buffer-list) - when (and (string= new-buf b) - (not (y-or-n-p - (format "Buffer `%s' already exists overwrite? " - new-buf)))) - do (setq new-buf (helm-read-string "GrepBufferName: " "*hgrep ")))) - (setq buf new-buf)) - (with-current-buffer (get-buffer-create buf) - (setq default-directory (or helm-ff-default-directory - (helm-default-directory) - default-directory)) - (setq buffer-read-only t) - (let ((inhibit-read-only t) - (map (make-sparse-keymap))) - (erase-buffer) - (insert "-*- mode: helm-grep -*-\n\n" - (format "%s Results for `%s':\n\n" src-name pattern)) - (save-excursion - (insert (with-current-buffer helm-buffer - (goto-char (point-min)) (forward-line 1) - (buffer-substring (point) (point-max))))) - (save-excursion - (while (not (eobp)) - (add-text-properties (point-at-bol) (point-at-eol) - `(keymap ,map - help-echo ,(concat - (get-text-property - (point) 'helm-grep-fname) - "\nmouse-1: set point\nmouse-2: jump to selection") - mouse-face highlight)) - (define-key map [mouse-1] 'mouse-set-point) - (define-key map [mouse-2] 'helm-grep-mode-mouse-jump) - (define-key map [mouse-3] 'ignore) - (forward-line 1)))) - (helm-grep-mode)) - (pop-to-buffer buf) - (message "Helm %s Results saved in `%s' buffer" src-name buf))) - -(defun helm-grep-mode-mouse-jump (event) - (interactive "e") - (let* ((window (posn-window (event-end event))) - (pos (posn-point (event-end event)))) - (with-selected-window window - (when (eq major-mode 'helm-grep-mode) - (goto-char pos) - (helm-grep-mode-jump))))) -(put 'helm-grep-mode-mouse-jump 'helm-only t) - -(define-derived-mode helm-grep-mode - special-mode "helm-grep" - "Major mode to provide actions in helm grep saved buffer. - -Special commands: -\\{helm-grep-mode-map}" - (set (make-local-variable 'helm-grep-last-cmd-line) - (with-helm-buffer helm-grep-last-cmd-line)) - (set (make-local-variable 'revert-buffer-function) - #'helm-grep-mode--revert-buffer-function)) -(put 'helm-grep-mode 'helm-only t) - -(defun helm-grep-mode--revert-buffer-function (&optional _ignore-auto _noconfirm) - (goto-char (point-min)) - (when (re-search-forward helm-grep-split-line-regexp nil t) (forward-line 0)) - (let ((inhibit-read-only t)) - (delete-region (point) (point-max))) - (message "Reverting buffer...") - (let ((process-connection-type - ;; Git needs a nil value otherwise it tries to use a pager. - (null (string-match-p "\\`git" helm-grep-last-cmd-line)))) - (set-process-sentinel - (start-file-process-shell-command - "hgrep" (generate-new-buffer "*hgrep revert*") helm-grep-last-cmd-line) - 'helm-grep-mode--sentinel))) - -(defun helm-grep-mode--sentinel (process event) - (when (string= event "finished\n") - (with-current-buffer (current-buffer) - (let ((inhibit-read-only t)) - (save-excursion - (cl-loop for l in (with-current-buffer (process-buffer process) - (prog1 (split-string (buffer-string) "\n") - (kill-buffer))) - for line = (if (string-match-p helm--ansi-color-regexp l) - (helm--ansi-color-apply l) l) - when (string-match helm-grep-split-line-regexp line) - do (insert (propertize - (car (helm-grep-filter-one-by-one line)) - ;; needed for wgrep. - 'helm-realvalue line) - "\n")))) - (when (fboundp 'wgrep-cleanup-overlays) - (wgrep-cleanup-overlays (point-min) (point-max))) - (message "Reverting buffer done")))) - -(defun helm-gm-next-file () - (interactive) - (helm-goto-next-or-prec-file 1)) - -(defun helm-gm-precedent-file () - (interactive) - (helm-goto-next-or-prec-file -1)) - -(defun helm-grep-mode-jump () - (interactive) - (helm-grep-action - (buffer-substring (point-at-bol) (point-at-eol))) - (helm-match-line-cleanup-pulse)) - -(defun helm-grep-mode-jump-other-window-1 (arg) - (condition-case nil - (progn - (when (or (eq last-command 'helm-grep-mode-jump-other-window-forward) - (eq last-command 'helm-grep-mode-jump-other-window-backward)) - (forward-line arg)) - (save-selected-window - (helm-grep-action (buffer-substring (point-at-bol) (point-at-eol)) - 'other-window) - (helm-match-line-cleanup-pulse) - (recenter))) - (error nil))) - -(defun helm-grep-mode-jump-other-window-forward (arg) - (interactive "p") - (helm-grep-mode-jump-other-window-1 arg)) - -(defun helm-grep-mode-jump-other-window-backward (arg) - (interactive "p") - (helm-grep-mode-jump-other-window-1 (- arg))) - -(defun helm-grep-mode-jump-other-window () - (interactive) - (let ((candidate (buffer-substring (point-at-bol) (point-at-eol)))) - (condition-case nil - (progn (helm-grep-action candidate 'other-window) - (helm-match-line-cleanup-pulse)) - (error nil)))) - - -;;; ack-grep types -;; -;; -(defun helm-grep-hack-types () - "Return a list of known ack-grep types." - (with-temp-buffer - ;; "--help-types" works with both 1.96 and 2.1+, while - ;; "--help types" works only with 1.96 Issue #422. - ;; `helm-grep-command' should return the ack executable - ;; when this function is used in the right context - ;; i.e After checking is we are using ack-grep with - ;; `helm-grep-use-ack-p'. - (call-process (helm-grep-command t) nil t nil "--help-types") - (goto-char (point-min)) - (cl-loop while (re-search-forward - "^ *--\\(\\[no\\]\\)\\([^. ]+\\) *\\(.*\\)" nil t) - collect (cons (concat (match-string 2) - " [" (match-string 3) "]") - (match-string 2)) - collect (cons (concat "no" (match-string 2) - " [" (match-string 3) "]") - (concat "no" (match-string 2)))))) - -(defun helm-grep-ack-types-transformer (candidates _source) - (cl-loop for i in candidates - if (stringp i) - collect (rassoc i helm-grep-ack-types-cache) - else - collect i)) - -(defvar helm-grep-ack-types-cache nil) -(defun helm-grep-read-ack-type () - "Select types for the '--type' argument of ack-grep." - (require 'helm-mode) - (require 'helm-adaptive) - (setq helm-grep-ack-types-cache (helm-grep-hack-types)) - (let ((types (helm-comp-read - "Types: " helm-grep-ack-types-cache - :name "*Ack-grep types*" - :marked-candidates t - :must-match t - :fc-transformer '(helm-adaptive-sort - helm-grep-ack-types-transformer) - :buffer "*helm ack-types*"))) - (mapconcat (lambda (type) (concat "--type=" type)) types " "))) - - -;;; grep extensions -;; -;; -(defun helm-grep-guess-extensions (files) - "Try to guess file extensions in FILES list when using grep recurse. -These extensions will be added to command line with --include arg of grep." - (cl-loop with ext-list = (list helm-grep-preferred-ext "*") - with lst = (if (file-directory-p (car files)) - (directory-files - (car files) nil - directory-files-no-dot-files-regexp) - files) - for i in lst - for ext = (file-name-extension i 'dot) - for glob = (and ext (not (string= ext "")) - (concat "*" ext)) - unless (or (not glob) - (and glob-list (member glob glob-list)) - (and glob-list (member glob ext-list)) - (and glob-list (member glob helm-grep-ignored-files))) - collect glob into glob-list - finally return (delq nil (append ext-list glob-list)))) - -(defun helm-grep-get-file-extensions (files) - "Try to return a list of file extensions to pass to '--include' arg of grep." - (require 'helm-adaptive) - (let* ((all-exts (helm-grep-guess-extensions - (mapcar 'expand-file-name files))) - (extensions (helm-comp-read "Search Only in: " all-exts - :marked-candidates t - :fc-transformer 'helm-adaptive-sort - :buffer "*helm grep exts*" - :name "*helm grep extensions*"))) - (when (listp extensions) ; Otherwise it is empty string returned by C-RET. - ;; If extensions is a list of one string containing spaces, - ;; assume user entered more than one glob separated by space(s) and - ;; split this string to pass it later to mapconcat. - ;; e.g '("*.el *.py") - (cl-loop for i in extensions - append (split-string-and-unquote i " "))))) - - -;;; Set up source -;; -;; -(defvar helm-grep-before-init-hook nil - "Hook that runs before initialization of the helm buffer.") - -(defvar helm-grep-after-init-hook nil - "Hook that runs after initialization of the helm buffer.") - -(defclass helm-grep-class (helm-source-async) - ((candidates-process :initform 'helm-grep-collect-candidates) - (filter-one-by-one :initform 'helm-grep-filter-one-by-one) - (keymap :initform helm-grep-map) - (pcre :initarg :pcre :initform nil - :documentation - " Backend is using pcre regexp engine when non--nil.") - (nohighlight :initform t) - (nomark :initform t) - (backend :initarg :backend - :initform nil - :documentation - " The grep backend that will be used. - It is actually used only as an internal flag - and don't set the backend by itself. - You probably don't want to modify this.") - (candidate-number-limit :initform 9999) - (help-message :initform 'helm-grep-help-message) - (history :initform 'helm-grep-history) - (action :initform 'helm-grep-actions) - (persistent-action :initform 'helm-grep-persistent-action) - (persistent-help :initform "Jump to line (`C-u' Record in mark ring)") - (requires-pattern :initform 2) - (before-init-hook :initform 'helm-grep-before-init-hook) - (after-init-hook :initform 'helm-grep-after-init-hook) - (group :initform 'helm-grep))) - -(defvar helm-source-grep nil) - -(defmethod helm--setup-source ((source helm-grep-class)) - (call-next-method) - (helm-aif (and helm-follow-mode-persistent - (if (eq (slot-value source 'backend) 'git) - helm-source-grep-git - helm-source-grep)) - (setf (slot-value source 'follow) - (assoc-default 'follow it)))) - -(cl-defun helm-do-grep-1 (targets &optional recurse backend exts - default-input input (source 'helm-source-grep)) - "Launch helm using backend BACKEND on a list of TARGETS files. - -When RECURSE is given and BACKEND is 'grep' use -r option of -BACKEND and prompt user for EXTS to set the --include args of BACKEND. -Interactively you can give more than one arg separated by space at prompt. -e.g - $Pattern: *.el *.py *.tex - -From lisp use the EXTS argument as a list of extensions as above. -If you are using ack-grep, you will be prompted for --type -instead and EXTS will be ignored. -If prompt is empty `helm-grep-ignored-files' are added to --exclude. - -Argument DEFAULT-INPUT is use as `default' arg of `helm' and INPUT -is used as `input' arg of `helm', See `helm' docstring. - -Arg BACKEND when non--nil specify which backend to use -It is used actually to specify 'zgrep' or 'git'. -When BACKEND 'zgrep' is used don't prompt for a choice -in recurse, and ignore EXTS, search being made recursively on files matching -`helm-zgrep-file-extension-regexp' only." - (let* (non-essential - (ack-rec-p (helm-grep-use-ack-p :where 'recursive)) - (exts (and recurse - ;; [FIXME] I could handle this from helm-walk-directory. - (not (eq backend 'zgrep)) ; zgrep doesn't handle -r opt. - (not ack-rec-p) - (or exts (helm-grep-get-file-extensions targets)))) - (include-files - (and exts - (mapconcat (lambda (x) - (concat "--include=" - (shell-quote-argument x))) - (if (> (length exts) 1) - (remove "*" exts) - exts) " "))) - (types (and (not include-files) - (not (eq backend 'zgrep)) - recurse - ack-rec-p - ;; When %e format spec is not specified - ;; ignore types and do not prompt for choice. - (string-match "%e" helm-grep-default-command) - (helm-grep-read-ack-type))) - (src-name (capitalize (helm-grep-command recurse backend))) - (com (cond ((eq backend 'zgrep) helm-default-zgrep-command) - ((eq backend 'git) helm-grep-git-grep-command) - (recurse helm-grep-default-recurse-command) - ;; When resuming, the local value of - ;; `helm-grep-default-command' is used, only git-grep - ;; should need this. - (t helm-grep-default-command)))) - ;; When called as action from an other source e.g *-find-files - ;; we have to kill action buffer. - (when (get-buffer helm-action-buffer) - (kill-buffer helm-action-buffer)) - ;; If `helm-find-files' haven't already started, - ;; give a default value to `helm-ff-default-directory' - ;; and set locally `default-directory' to this value . See below [1]. - (unless helm-ff-default-directory - (setq helm-ff-default-directory default-directory)) - ;; We need to store these vars locally - ;; to pass infos later to `helm-resume'. - (helm-set-local-variable - 'helm-zgrep-recurse-flag (and recurse (eq backend 'zgrep)) - 'helm-grep-last-targets targets - 'helm-grep-include-files (or include-files types) - 'helm-grep-in-recurse recurse - 'helm-grep-use-zgrep (eq backend 'zgrep) - 'helm-grep-default-command com - 'helm-input-idle-delay helm-grep-input-idle-delay - 'default-directory helm-ff-default-directory) ;; [1] - ;; Setup the source. - (set source (helm-make-source src-name 'helm-grep-class - :backend backend - :pcre (string-match-p "\\`ack" com))) - (helm - :sources source - :buffer (format "*helm %s*" (helm-grep-command recurse backend)) - :default default-input - :input input - :keymap helm-grep-map - :history 'helm-grep-history - :truncate-lines helm-grep-truncate-lines))) - - -;;; zgrep -;; -;; -(defun helm-ff-zgrep-1 (flist recursive) - (unwind-protect - (let* ((def-dir (or helm-ff-default-directory - default-directory)) - (only (if recursive - (or (gethash def-dir helm-rzgrep-cache) - (puthash - def-dir - (helm-walk-directory - def-dir - :directories nil - :path 'full - :match helm-zgrep-file-extension-regexp) - helm-rzgrep-cache)) - flist))) - (helm-do-grep-1 only recursive 'zgrep)) - (setq helm-zgrep-recurse-flag nil))) - - -;;; transformers -;; -;; -(defun helm-grep-split-line (line) - "Split a grep output line." - ;; The output of grep may send a truncated line in this chunk, - ;; so don't split until grep line is valid, that is - ;; once the second part of the line comes with next chunk - ;; send by process. - (when (string-match helm-grep-split-line-regexp line) - ;; Don't use split-string because buffer/file name or string - ;; may contain a ":". - (cl-loop for n from 1 to 3 collect (match-string n line)))) - -(defun helm-grep--filter-candidate-1 (candidate &optional dir) - (let* ((root (or dir (and helm-grep-default-directory-fn - (funcall helm-grep-default-directory-fn)))) - (ansi-p (string-match-p helm--ansi-color-regexp candidate)) - (line (if ansi-p (helm--ansi-color-apply candidate) candidate)) - (split (helm-grep-split-line line)) - (fname (if (and root split) - ;; Filename should always be provided as a local - ;; path, if the root directory is remote, the - ;; tramp prefix will be added before executing - ;; action, see `helm-grep-action' and issue #2032. - (expand-file-name (car split) - (or (file-remote-p root 'localname) - root)) - (car-safe split))) - (lineno (nth 1 split)) - (str (nth 2 split)) - (display-fname (cl-ecase helm-grep-file-path-style - (basename (and fname (file-name-nondirectory fname))) - (absolute fname) - (relative (and fname root - (file-relative-name fname root)))))) - (if (and display-fname lineno str) - (cons (concat (propertize display-fname - 'face 'helm-grep-file - 'help-echo (abbreviate-file-name fname) - 'helm-grep-fname fname) - ":" - (propertize lineno 'face 'helm-grep-lineno) - ":" - (if ansi-p str (helm-grep-highlight-match str t))) - line) - ""))) - -(defun helm-grep-filter-one-by-one (candidate) - "`filter-one-by-one' transformer function for `helm-do-grep-1'." - (let ((helm-grep-default-directory-fn - (or helm-grep-default-directory-fn - (lambda () (or helm-ff-default-directory - (and (null (eq major-mode 'helm-grep-mode)) - (helm-default-directory)) - default-directory))))) - (if (consp candidate) - ;; Already computed do nothing (default as input). - candidate - (and (stringp candidate) - (helm-grep--filter-candidate-1 candidate))))) - -(defun helm-grep-highlight-match (str &optional multi-match) - "Highlight in string STR all occurences matching `helm-pattern'." - (let (beg end) - (condition-case-unless-debug nil - (with-temp-buffer - (insert (propertize str 'read-only nil)) ; Fix (#1176) - (goto-char (point-min)) - (cl-loop for reg in - (if multi-match - ;; (m)occur. - (cl-loop for r in (helm-mm-split-pattern - helm-pattern) - unless (string-match "\\`!" r) - collect - (helm-aif (and helm-migemo-mode - (assoc r helm-mm--previous-migemo-info)) - (cdr it) r)) - ;; async sources (grep, gid etc...) - (list helm-input)) - do - (while (and (re-search-forward reg nil t) - (> (- (setq end (match-end 0)) - (setq beg (match-beginning 0))) 0)) - (helm-add-face-text-properties beg end 'helm-grep-match)) - do (goto-char (point-min))) - (buffer-string)) - (error nil)))) - - -;;; Grep from buffer list -;; -;; -(defun helm-grep-buffers-1 (candidate &optional zgrep) - "Run grep on all file--buffers or CANDIDATE if it is a file--buffer. -If one of selected buffers is not a file--buffer, -it is ignored and grep will run on all others file--buffers. -If only one candidate is selected and it is not a file--buffer, -switch to this buffer and run `helm-occur'. -If a prefix arg is given run grep on all buffers ignoring non--file-buffers." - (let* ((prefarg (or current-prefix-arg helm-current-prefix-arg)) - (helm-ff-default-directory - (if (and helm-ff-default-directory - (file-remote-p helm-ff-default-directory)) - default-directory - helm-ff-default-directory)) - (cands (if prefarg - (buffer-list) - (helm-marked-candidates))) - (win-conf (current-window-configuration)) - ;; Non--fname and remote buffers are ignored. - (bufs (cl-loop for buf in cands - for fname = (buffer-file-name (get-buffer buf)) - when (and fname (not (file-remote-p fname))) - collect (expand-file-name fname)))) - (if bufs - (if zgrep - (helm-do-grep-1 bufs nil 'zgrep) - (helm-do-grep-1 bufs)) - ;; bufs is empty, thats mean we have only CANDIDATE - ;; and it is not a buffer-filename, fallback to occur. - (switch-to-buffer candidate) - (when (get-buffer helm-action-buffer) - (kill-buffer helm-action-buffer)) - (helm-occur) - (when (eq helm-exit-status 1) - (set-window-configuration win-conf))))) - -(defun helm-grep-buffers (candidate) - "Action to grep buffers." - (helm-grep-buffers-1 candidate)) - -(defun helm-zgrep-buffers (candidate) - "Action to zgrep buffers." - (helm-grep-buffers-1 candidate 'zgrep)) - - -;;; Helm interface for pdfgrep -;; pdfgrep program -;; and a pdf-reader (e.g xpdf) are needed. -;; -(defvar helm-pdfgrep-default-function 'helm-pdfgrep-init) -(defun helm-pdfgrep-init (only-files &optional recurse) - "Start an asynchronous pdfgrep process in ONLY-FILES list." - (let* ((default-directory (or helm-ff-default-directory - default-directory)) - (fnargs (helm-grep-prepare-candidates - (if (file-remote-p default-directory) - (mapcar (lambda (x) - (file-remote-p x 'localname)) - only-files) - only-files) - default-directory)) - (cmd-line (format (if recurse - helm-pdfgrep-default-recurse-command - helm-pdfgrep-default-command) - helm-pattern - fnargs)) - process-connection-type) - ;; Start pdf grep process. - (helm-log "Starting Pdf Grep process in directory `%s'" default-directory) - (helm-log "Command line used was:\n\n%s" - (concat ">>> " (propertize cmd-line 'face 'helm-grep-cmd-line) "\n\n")) - (prog1 - (start-file-process-shell-command - "pdfgrep" helm-buffer cmd-line) - (message nil) - (set-process-sentinel - (get-buffer-process helm-buffer) - (lambda (_process event) - (if (string= event "finished\n") - (with-helm-window - (setq mode-line-format - '(" " mode-line-buffer-identification " " - (:eval (format "L%s" (helm-candidate-number-at-point))) " " - (:eval (propertize - (format "[Pdfgrep Process Finish - %s result(s)] " - (max (1- (count-lines - (point-min) (point-max))) 0)) - 'face 'helm-grep-finish)))) - (force-mode-line-update) - (when helm-allow-mouse - (helm--bind-mouse-for-selection helm-selection-point))) - (helm-log "Error: Pdf grep %s" - (replace-regexp-in-string "\n" "" event)))))))) - -(defun helm-do-pdfgrep-1 (only &optional recurse) - "Launch pdfgrep with a list of ONLY files." - (unless (executable-find "pdfgrep") - (error "Error: No such program `pdfgrep'.")) - (let (helm-grep-in-recurse) ; recursion is implemented differently in *pdfgrep. - ;; When called as action from an other source e.g *-find-files - ;; we have to kill action buffer. - (when (get-buffer helm-action-buffer) - (kill-buffer helm-action-buffer)) - (setq helm-pdfgrep-targets only) - (helm - :sources (helm-build-async-source "PdfGrep" - :init (lambda () - ;; If `helm-find-files' haven't already started, - ;; give a default value to `helm-ff-default-directory'. - (setq helm-ff-default-directory (or helm-ff-default-directory - default-directory))) - :candidates-process (lambda () - (funcall helm-pdfgrep-default-function - helm-pdfgrep-targets recurse)) - :nohighlight t - :nomark t - :filter-one-by-one #'helm-grep-filter-one-by-one - :candidate-number-limit 9999 - :history 'helm-grep-history - :keymap helm-pdfgrep-map - :help-message 'helm-pdfgrep-help-message - :action #'helm-pdfgrep-action - :persistent-help "Jump to PDF Page" - :requires-pattern 2) - :buffer "*helm pdfgrep*" - :history 'helm-grep-history))) - -(defun helm-pdfgrep-action (candidate) - (helm-grep-action candidate 'pdf)) - -(defun helm-pdfgrep-action-1 (_split pageno fname) - (save-selected-window - (start-file-process-shell-command - "pdf-reader" nil - (format-spec helm-pdfgrep-default-read-command - (list (cons ?f fname) (cons ?p pageno)))))) - -;;; AG - PT - RG -;; -;; https://github.com/ggreer/the_silver_searcher -;; https://github.com/monochromegane/the_platinum_searcher -;; https://github.com/BurntSushi/ripgrep - -(defcustom helm-grep-ag-command - "ag --line-numbers -S --hidden --color --nogroup %s %s %s" - "The default command for AG, PT or RG. - -Takes three format specs, the first for type(s), the second for pattern -and the third for directory. - -You can use safely \"--color\" (used by default) with AG RG and PT. - -For ripgrep here is the command line to use: - - rg --color=always --smart-case --no-heading --line-number %s %s %s - -NOTE: Old versions of ripgrep was not supporting colors in emacs and a -workaround had to be used (i.e prefixing command line with -\"TERM=eterm-color\"), this is no more needed. -See issue for more infos. - -You must use an output format that fit with helm grep, that is: - - \"filename:line-number:string\" - -The option \"--nogroup\" allow this. -The option \"--line-numbers\" is also mandatory except with PT (not supported). -For RG the options \"--no-heading\" and \"--line-number\" are the ones to use. - -When modifying the default colors of matches with e.g \"--color-match\" option of AG -you may want to modify as well `helm-grep-ag-pipe-cmd-switches' to have all matches -colorized with same color in multi match." - :group 'helm-grep - :type 'string) - -(defun helm-grep--ag-command () - (car (helm-remove-if-match - "\\`[A-Z]*=" (split-string helm-grep-ag-command)))) - -(defun helm-grep-ag-get-types () - "Returns a list of AG types if available with AG version. -See AG option \"--list-file-types\" -Ripgrep (rg) types are also supported if this backend is used." - (with-temp-buffer - (let* ((com (helm-grep--ag-command)) - (ripgrep (string= com "rg")) - (regex (if ripgrep "^\\(.*\\):" "^ *\\(--[a-z]*\\)")) - (prefix (if ripgrep "-t " ""))) - (when (equal (call-process com - nil t nil - (if ripgrep - "--type-list" "--list-file-types")) 0) - (goto-char (point-min)) - (cl-loop while (re-search-forward regex nil t) - for type = (match-string 1) - collect (cons type (concat prefix type))))))) - -(defun helm-grep-ag-prepare-cmd-line (pattern directory &optional type) - "Prepare AG command line to search PATTERN in DIRECTORY. -When TYPE is specified it is one of what returns `helm-grep-ag-get-types' -if available with current AG version." - (let* ((patterns (helm-mm-split-pattern pattern t)) - (pipe-switches (mapconcat 'identity helm-grep-ag-pipe-cmd-switches " ")) - (pipe-cmd (helm-acase (helm-grep--ag-command) - (("ag" "pt") - (format "%s -S --color%s" it (concat " " pipe-switches))) - ("rg" (format "rg -N -S --color=always%s" - (concat " " pipe-switches))))) - (cmd (format helm-grep-ag-command - (mapconcat 'identity type " ") - (shell-quote-argument (car patterns)) - (shell-quote-argument directory)))) - (helm-aif (cdr patterns) - (concat cmd (cl-loop for p in it concat - (format " | %s %s" - pipe-cmd (shell-quote-argument p)))) - cmd))) - -(defun helm-grep-ag-init (directory &optional type) - "Start AG process in DIRECTORY maybe searching only files of type TYPE." - (let ((default-directory (or helm-ff-default-directory - (helm-default-directory) - default-directory)) - (cmd-line (helm-grep-ag-prepare-cmd-line - helm-pattern (or (file-remote-p directory 'localname) - directory) - type)) - (start-time (float-time)) - (proc-name (helm-grep--ag-command))) - (set (make-local-variable 'helm-grep-last-cmd-line) cmd-line) - (helm-log "Starting %s process in directory `%s'" - proc-name directory) - (helm-log "Command line used was:\n\n%s" - (concat ">>> " cmd-line "\n\n")) - (prog1 - (start-file-process-shell-command - proc-name helm-buffer cmd-line) - (set-process-sentinel - (get-buffer-process helm-buffer) - (lambda (process event) - (let* ((err (process-exit-status process)) - (noresult (= err 1))) - (cond (noresult - (with-helm-buffer - (insert (concat "* Exit with code 1, no result found," - " command line was:\n\n " - (propertize helm-grep-last-cmd-line - 'face 'helm-grep-cmd-line))) - (setq mode-line-format - `(" " mode-line-buffer-identification " " - (:eval (format "L%s" (helm-candidate-number-at-point))) " " - (:eval (propertize - (format - "[%s process finished - (no results)] " - ,(upcase proc-name)) - 'face 'helm-grep-finish)))))) - ((string= event "finished\n") - (helm-log "%s process finished with %s results in %fs" - proc-name - (helm-get-candidate-number) - (- (float-time) start-time)) - (helm-maybe-show-help-echo) - (with-helm-window - (setq mode-line-format - `(" " mode-line-buffer-identification " " - (:eval (format "L%s" (helm-candidate-number-at-point))) " " - (:eval (propertize - (format - "[%s process finished in %.2fs - (%s results)] " - ,(upcase proc-name) - ,(- (float-time) start-time) - (helm-get-candidate-number)) - 'face 'helm-grep-finish)))) - (force-mode-line-update) - (when helm-allow-mouse - (helm--bind-mouse-for-selection helm-selection-point)))) - (t (helm-log - "Error: %s %s" - proc-name - (replace-regexp-in-string "\n" "" event)))))))))) - -(defclass helm-grep-ag-class (helm-source-async) - ((nohighlight :initform t) - (pcre :initarg :pcre :initform t - :documentation - " Backend is using pcre regexp engine when non--nil.") - (keymap :initform helm-grep-map) - (history :initform 'helm-grep-ag-history) - (help-message :initform 'helm-grep-help-message) - (filter-one-by-one :initform 'helm-grep-filter-one-by-one) - (persistent-action :initform 'helm-grep-persistent-action) - (persistent-help :initform "Jump to line (`C-u' Record in mark ring)") - (candidate-number-limit :initform 99999) - (requires-pattern :initform 2) - (nomark :initform t) - (action :initform 'helm-grep-actions) - (group :initform 'helm-grep))) - -(defvar helm-source-grep-ag nil) - -(defmethod helm--setup-source ((source helm-grep-ag-class)) - (call-next-method) - (helm-aif (and helm-follow-mode-persistent - helm-source-grep-ag - (assoc-default 'follow helm-source-grep-ag)) - (setf (slot-value source 'follow) it))) - -(defun helm-grep-ag-1 (directory &optional type) - "Start helm ag in DIRECTORY maybe searching in files of type TYPE." - (setq helm-source-grep-ag - (helm-make-source (upcase (helm-grep--ag-command)) 'helm-grep-ag-class - :header-name (lambda (name) - (format "%s [%s]" - name (abbreviate-file-name directory))) - :candidates-process - (lambda () (helm-grep-ag-init directory type)))) - (helm-set-local-variable 'helm-input-idle-delay helm-grep-input-idle-delay) - (helm :sources 'helm-source-grep-ag - :keymap helm-grep-map - :history 'helm-grep-ag-history - :truncate-lines helm-grep-truncate-lines - :buffer (format "*helm %s*" (helm-grep--ag-command)))) - -(defun helm-grep-ag (directory with-types) - "Start grep AG in DIRECTORY. -When WITH-TYPES is non-nil provide completion on AG types." - (require 'helm-adaptive) - (helm-grep-ag-1 directory - (helm-aif (and with-types - (helm-grep-ag-get-types)) - (helm-comp-read - "Ag type: " it - :must-match t - :marked-candidates t - :fc-transformer 'helm-adaptive-sort - :buffer "*helm ag types*")))) - -;;; Git grep -;; -;; -(defvar helm-source-grep-git nil) - -(defcustom helm-grep-git-grep-command - "git --no-pager grep -n%cH --color=always --full-name -e %p -- %f" - "The git grep default command line. -The option \"--color=always\" can be used safely. -The color of matched items can be customized in your .gitconfig -See `helm-grep-default-command' for more infos. - -The \"--exclude-standard\" and \"--no-index\" switches allow -skipping unwanted files specified in ~/.gitignore_global -and searching files not already staged (not enabled by default). - -You have also to enable this in global \".gitconfig\" with - \"git config --global core.excludesfile ~/.gitignore_global\"." - :group 'helm-grep - :type 'string) - -(defun helm-grep-git-1 (directory &optional all default input) - "Run git-grep on DIRECTORY. -If DIRECTORY is not inside or part of a git repo exit with error. -If optional arg ALL is non-nil grep the whole repo otherwise start -at DIRECTORY. -Arg DEFAULT is what you will have with `next-history-element', -arg INPUT is what you will have by default at prompt on startup." - (require 'vc) - (let* (helm-grep-default-recurse-command - ;; Expand filename of each candidate with the git root dir. - ;; The filename will be in the helm-grep-fname prop. - (helm-grep-default-directory-fn (lambda () - (vc-find-root directory ".git"))) - (helm-ff-default-directory (funcall helm-grep-default-directory-fn))) - (cl-assert helm-ff-default-directory nil "Not inside a Git repository") - (helm-do-grep-1 (if all '("") `(,(expand-file-name directory))) - nil 'git nil default input 'helm-source-grep-git))) - - -;;;###autoload -(defun helm-do-grep-ag (arg) - "Preconfigured helm for grepping with AG in `default-directory'. -With prefix-arg prompt for type if available with your AG version." - (interactive "P") - (require 'helm-files) - (helm-grep-ag (expand-file-name default-directory) arg)) - -;;;###autoload -(defun helm-grep-do-git-grep (arg) - "Preconfigured helm for git-grepping `default-directory'. -With a prefix arg ARG git-grep the whole repository." - (interactive "P") - (require 'helm-files) - (helm-grep-git-1 default-directory arg)) - - -(provide 'helm-grep) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-grep.el ends here diff --git a/elpa/helm-20191031.725/helm-help.el b/elpa/helm-20191031.725/helm-help.el deleted file mode 100644 index f86ae90e..00000000 --- a/elpa/helm-20191031.725/helm-help.el +++ /dev/null @@ -1,1821 +0,0 @@ -;;; helm-help.el --- Help messages for Helm. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: -(require 'helm) - - -(defgroup helm-help nil - "Embedded help for `helm'." - :group 'helm) - -(defface helm-helper - '((t :inherit helm-header)) - "Face for Helm help string in minibuffer." - :group 'helm-help) - -(defvar helm-help--string-list '(helm-help-message - helm-buffer-help-message - helm-ff-help-message - helm-read-file-name-help-message - helm-generic-file-help-message - helm-grep-help-message - helm-pdfgrep-help-message - helm-etags-help-message - helm-ucs-help-message - helm-bookmark-help-message - helm-esh-help-message - helm-buffers-ido-virtual-help-message - helm-moccur-help-message - helm-top-help-message - helm-el-package-help-message - helm-M-x-help-message - helm-imenu-help-message - helm-colors-help-message - helm-semantic-help-message - helm-kmacro-help-message)) - -(defvar helm-documentation-buffer-name "*helm documentation*") - -;;;###autoload -(defun helm-documentation () - "Preconfigured Helm for Helm documentation. -With a prefix arg refresh the documentation. - -Find here the documentation of all documented sources." - (interactive) - (let ((buf (get-buffer-create helm-documentation-buffer-name))) - (switch-to-buffer buf) - (set-buffer buf) - (let ((inhibit-read-only t)) - (erase-buffer) - (cl-loop for elm in helm-help--string-list - for str = (helm-interpret-value elm) - do (insert (substitute-command-keys str) "\n\n")) - (org-mode)) - (setq buffer-read-only t) - (view-mode))) - - -;;; Local help messages. - -;;; `helm-buffer-list' help -;; -;; -(defvar helm-buffer-help-message - "* Helm Buffer - -** Tips - -*** Completion - -**** Major-mode - -You can enter a partial major-mode name (e.g. lisp, sh) to narrow down buffers. -To specify the major-mode, prefix it with \"*\" e.g. \"*lisp\". - -If you want to match all buffers but the ones with a specific major-mode -\(negation), prefix the major-mode with \"!\" e.g. \"*!lisp\". - -If you want to specify more than one major-mode, separate them with \",\", -e.g. \"*!lisp,!sh,!fun\" lists all buffers but the ones in lisp-mode, sh-mode -and fundamental-mode. - -Then enter a space followed by a pattern to narrow down to buffers matching this -pattern. - -**** Search inside buffers - -If you enter a space and a pattern prefixed by \"@\", Helm searches for text -matching this pattern \*inside* the buffer (i.e. not in the name of the buffer). - -If you enter a pattern prefixed with an escaped \"@\", Helm searches for a -buffer matching \"@pattern\" but does not search inside. - -**** Search by directory name - -If you prefix the pattern with \"/\", Helm matches over the directory names -of the buffers. - -This feature can be used to narrow down the search to one directory while -subsequent strings entered after a space match over the buffer name only. - -Note that negation is not supported for matching on buffer filename. - -Starting from Helm v1.6.8, you can specify more than one directory. - -**** Fuzzy matching - -`helm-buffers-fuzzy-matching' turns on fuzzy matching on buffer names, but not -on directory names or major modes. A pattern starting with \"^\" disables fuzzy -matching and matches by exact regexp. - -**** Examples - -With the following pattern - - \"*lisp ^helm @moc\" - -Helm narrows down the list by selecting only the buffers that are in lisp mode, -start with \"helm\" and which content matches \"moc\". - -Without the \"@\" - - \"*lisp ^helm moc\" - -Helm looks for lisp mode buffers starting with \"helm\" and containing \"moc\" -in their name. - -With this other pattern - - \"*!lisp !helm\" - -Helm narrows down to buffers that are not in \"lisp\" mode and that do not match -\"helm\". - -With this last pattern - - /helm/ w3 - -Helm narrows down to buffers that are in any \"helm\" subdirectory and -matching \"w3\". - -*** Creating buffers - -When creating a new buffer, use `\\[universal-argument]' to choose a mode from a -list. This list is customizable, see `helm-buffers-favorite-modes'. - -*** Killing buffers - -You can kill buffers either one by one or all the marked buffers at once. - -One kill-buffer command leaves Helm while the other is persistent. Run the -persistent kill-buffer command either with the regular -`helm-execute-persistent-action' called with a prefix argument (`\\[universal-argument] \\\\[helm-execute-persistent-action]') -or with its specific command `helm-buffer-run-kill-persistent'. See the -bindings below. - -*** Switching to buffers - -To switch to a buffer, press RET, to switch to a buffer in another window, select this buffer -and press \\\\[helm-buffer-switch-other-window], when called with a prefix arg -the buffer will be displayed vertically in other window. -If you mark more than one buffer, the marked buffers will be displayed in different windows. - -*** Saving buffers - -If buffer is associated to a file and is modified, it is by default colorized in orange, -see [[Meaning of colors and prefixes for buffers][Meaning of colors and prefixes for buffers]]. -You can save these buffers with \\\\[helm-buffer-save-persistent]. -If you want to save all these buffers, you can mark them with \\[helm-buffers-mark-similar-buffers] -and save them with \\[helm-buffer-save-persistent], you can also do this in one step with -\\[helm-buffer-run-save-some-buffers], note that you will not be asked for confirmation. - -*** Meaning of colors and prefixes for buffers - -Remote buffers are prefixed with '@'. -Red => Buffer's file was modified on disk by an external process. -Indianred2 => Buffer exists but its file has been deleted. -Orange => Buffer is modified and not saved to disk. -Italic => A non-file buffer. -Yellow => Tramp archive buffer. - -** Commands -\\ -\\[helm-buffer-run-zgrep]\t\tGrep Buffer(s) works as zgrep too (`\\[universal-argument]' to grep all buffers but non-file buffers). -\\[helm-buffers-run-multi-occur]\t\tMulti-Occur buffer or marked buffers (`\\[universal-argument]' to toggle force-searching current-buffer). -\\[helm-buffer-switch-other-window]\t\tSwitch to other window. -\\[helm-buffer-switch-other-frame]\t\tSwitch to other frame. -\\[helm-buffers-run-browse-project]\t\tBrowse project from buffer. -\\[helm-buffer-run-query-replace-regexp]\t\tQuery-replace-regexp in marked buffers. -\\[helm-buffer-run-query-replace]\t\tQuery-replace in marked buffers. -\\[helm-buffer-run-ediff]\t\tEdiff current buffer with candidate. With two marked buffers, ediff those buffers. -\\[helm-buffer-run-ediff-merge]\t\tEdiff-merge current buffer with candidate. With two marked buffers, ediff-merge those buffers. -\\[helm-buffer-diff-persistent]\t\tToggle Diff-buffer with saved file without leaving Helm. -\\[helm-buffer-revert-persistent]\t\tRevert buffer without leaving Helm. -\\[helm-buffer-save-persistent]\t\tSave buffer without leaving Helm. -\\[helm-buffer-run-save-some-buffers]\t\tSave all unsaved buffers. -\\[helm-buffer-run-kill-buffers]\t\tDelete marked buffers and leave Helm. -\\[helm-buffer-run-kill-persistent]\t\tDelete buffer without leaving Helm. -\\[helm-buffer-run-rename-buffer]\t\tRename buffer. -\\[helm-toggle-all-marks]\t\tToggle all marks. -\\[helm-mark-all]\t\tMark all. -\\[helm-toggle-buffers-details]\t\tToggle details. -\\[helm-buffers-toggle-show-hidden-buffers]\t\tShow hidden buffers. -\\[helm-buffers-mark-similar-buffers]\t\tMark all buffers of the same type (color) as current buffer.") - -;;; Find files help (`helm-find-files') -;; -;; -(defvar helm-ff-help-message - "* Helm Find Files - -** Tips - -*** Navigation summary - -For a better experience you can enable auto completion by setting -`helm-ff-auto-update-initial-value' to non-nil in your init file. It is not -enabled by default to not confuse new users. - -**** Navigate with arrow keys - -You can use and arrows to go down or up one level, to enable -this customize `helm-ff-lynx-style-map'. -This is disabled by default. -Note that using `setq' will NOT work. - -**** Use `\\\\[helm-execute-persistent-action]' (persistent action) on a directory to go down one level - -On a symlinked directory a prefix argument expands to its true name. - -**** Use `\\\\[helm-find-files-up-one-level]' or `DEL' on a directory to go up one level - -***** `DEL' behavior - -`DEL' by default is deleting char backward. - -But when `helm-ff-DEL-up-one-level-maybe' is non nil `DEL' behave -differently depending of helm-pattern contents, it go up one -level if pattern is a directory endings with \"/\" or disable HFF -auto update and delete char backward if pattern is a filename or -refer to a non existing path. Going up one level can be disabled -if necessary by deleting \"/\" at end of pattern using -\\\\[backward-char] and \\[helm-delete-minibuffer-contents]. - -Note that when deleting char backward, helm takes care of -disabling update letting you the time to edit your pattern for -e.g. renaming a file or creating a new file or directory. -When `helm-ff-auto-update-initial-value' is non nil you may want to -disable it temporarily, see [[Toggle auto-completion with `C-c DEL'][Toggle auto-completion with `C-c DEL']] for this. - -**** Use `\\\\[helm-find-files-down-last-level]' to walk back the resulting tree of all the `\\\\[helm-find-files-up-one-level]' or DEL you did - -The tree is reinitialized each time you browse a new tree with -`\\\\[helm-execute-persistent-action]' or by entering some pattern in the prompt. - -**** `RET' behavior - -It behaves differently depending on `helm-selection' (current candidate in helm-buffer): - -- candidate basename is \".\" => Open it in dired. -- candidate is a directory => Expand it. -- candidate is a file => Open it. - -If you have marked candidates and you press RET on a directory, -helm will navigate to this directory, if you want to exit with -RET with default action with these marked candidates, press RET -on a second time while you are on the root of this directory -e.g. \"/home/you/dir/.\" or press RET on any file which is not a -directory. You can also exit with default action at any moment -with `f1'. - -Note that when copying, renaming, etc. from `helm-find-files' the -destination file is selected with `helm-read-file-name'. - -To avoid confusion when using `read-file-name' or `read-directory-name', `RET' -follows its standard Emacs behaviour, i.e. it exits the minibuffer as soon as -you press `RET'. If you want the same behavior as in `helm-find-files', bind -`helm-ff-RET' to the `helm-read-file-map': - - (define-key helm-read-file-map (kbd \"RET\") 'helm-ff-RET) - -**** `TAB' behavior - -Normally `TAB' is bound to `helm-select-action' in helm-map which -display the action menu. - -You can change this behavior by setting in `helm-find-files-map' -a new command for `TAB': - - (define-key helm-find-files-map (kbd \"C-i\") 'helm-ff-TAB) - -It will then behave slighly differently -depending of `helm-selection': - -- candidate basename is \".\" => open the action menu. -- candidate is a directory => expand it (behave as \\\\[helm-execute-persistent-action]). -- candidate is a file => open action menu. - -Called with a prefix arg open menu unconditionally. - -*** Find file at point - -Helm uses `ffap' partially or completely to find file at point depending on the -value of `helm-ff-guess-ffap-filenames': if non-nil, support is complete -\(annoying), if nil, support is partial. - -Note that when the variable -`helm-ff-allow-non-existing-file-at-point' is non nil Helm will -insert the filename at point even if file with this name doesn't -exists. If non existing file at point ends with numbers prefixed -with \":\" the \":\" and numbers are stripped. - -**** Find file at line number - -When text at point is in the form of - - ~/elisp/helm/helm.el:1234 - -Helm finds this file at the indicated line number, here 1234. - -**** Find URL at point - -When a URL is found at point, Helm expands to that URL only. -Pressing `RET' opens that URL using `browse-url-browser-function'. - -**** Find e-mail address at point - -When an e-mail address is found at point, Helm expands to this e-mail address -prefixed with \"mailto:\". Pressing `RET' opens a message buffer with that -e-mail address. - -*** Quick pattern expansion - -**** Enter `~/' at end of pattern to quickly reach home directory - -**** Enter `/' at end of pattern to quickly reach the file system root - -**** Enter `./' at end of pattern to quickly reach `default-directory' - -\(As per its value at the beginning of the session.) - -If you already are in the `default-directory' this will move the cursor to the top. - -**** Enter `../' at end of pattern will reach upper directory, moving cursor to the top - -This is different from using `\\\\[helm-find-files-up-one-level]' in that it moves -the cursor to the top instead of remaining on the previous subdir name. - -**** Enter `..name/' at end of pattern to start a recursive search - -It searches directories matching \"name\" under the current directory, see the -\"Recursive completion on subdirectories\" section below for more details. - -**** Any environment variable (e.g. `$HOME') at end of pattern gets expanded - -**** Any valid filename yanked after pattern gets expanded - -**** Special case: URL at point - -The quick expansions do not take effect after end a URL, you must kill the -pattern first (`\\[helm-delete-minibuffer-contents]'). - -*** Helm-find-files supports fuzzy matching - -It starts from the third character of the pattern. - -For instance \"fob\" or \"fbr\" will complete \"foobar\" but \"fb\" needs a -third character in order to complete it. - -*** Use `\\[universal-argument] \\[helm-execute-persistent-action]' or `\\[helm-follow-action-forward]' to display an image - -*** `\\[helm-execute-persistent-action]' on a filename expands to that filename in the Helm buffer - -Second hit displays the buffer filename. -Third hit kills the buffer filename. -Note: `\\[universal-argument] \\[helm-execute-persistent-action]' displays the buffer directly. - -*** Browse images directories with `helm-follow-mode' and navigate up/down - -You can also use `helm-follow-action-forward' and `helm-follow-action-backward' with -`\\[helm-follow-action-forward]' and `\\[helm-follow-action-backward]' respectively. - -*** Toggle auto-completion with `\\[helm-ff-run-toggle-auto-update]' - -It is useful when trying to create a new file or directory and you don't want -Helm to complete what you are writing. - -Note: On a terminal, the default binding `C-' may not work. -In this case use `C-c '. - -*** You can create a new directory and a new file at the same time - -Simply write the path in the prompt and press `RET', e.g. -\"~/new/newnew/newnewnew/my_newfile.txt\". - -*** To create a new directory, append a \"/\" to the new name and press `RET' - -*** To create a new file, enter a filename not ending with \"/\" - -Note that when you enter a new name, this one is prefixed with -\[?] if you are in a writable directory. If you are in a directory -where you have no write permission the new file name is not -prefixed and is colored in red. There is not such distinction -when using tramp, new filename just appear on top of buffer. - -*** Recursive search from Helm-find-files - -**** You can use Helm-browse-project (see binding below) - -- With no prefix argument: -If the current directory is under version control with either git or hg and -helm-ls-git and/or helm-ls-hg are installed, it lists all the files under -version control. Otherwise it falls back to Helm-find-files. See -https://github.com/emacs-helm/helm-ls-git and -https://github.com/emacs-helm/helm-ls-hg. - -- With one prefix argument: -List all the files under this directory and other subdirectories -\(recursion) and this list of files will be cached. - -- With two prefix arguments: -Same but the cache is refreshed. - -**** You can start a recursive search with \"locate\" or \"find\" - -See \"Note\" in the [[Recursive completion on subdirectories][section on subdirectories]]. - -Using \"locate\", you can enable the local database with a prefix argument. If the -local database doesn't already exists, you will be prompted for its creation. -If it exists and you want to refresh it, give it two prefix args. - -When using locate the helm-buffer remains empty until you type something. -Regardless Helm uses the basename of the pattern entered in the helm-find-files -session by default. Hitting `\\[next-history-element]' should just kick in the -locate search with this pattern. If you want Helm to automatically do this, add -`helm-source-locate' to `helm-sources-using-default-as-input'. - -**** Recursive completion on subdirectories - -Starting from the directory you are currently browsing, it is possible to have -completion of all directories underneath. Say you are at \"/home/you/foo/\" and -you want to go to \"/home/you/foo/bar/baz/somewhere/else\", simply type -\"/home/you/foo/..else\" and hit `\\[helm-execute-persistent-action]' or enter -the final \"/\". Helm will then list all possible directories under \"foo\" -matching \"else\". - -Entering two spaces before \"else\" instead of two dots also works. - -Note: Completion on subdirectories uses \"locate\" as backend, you can configure -the command with `helm-locate-recursive-dirs-command'. Because this completion -uses an index, the directory tree displayed may be out-of-date and not reflect -the latest change until you update the index (using \"updatedb\" for \"locate\"). - -If for some reason you cannot use an index, the \"find\" command from -\"findutils\" can be used instead. It will be slower though. You need to pass -the basedir as first argument of \"find\" and the subdir as the value for -'-(i)regex' or '-(i)name' with the two format specs that are mandatory in -`helm-locate-recursive-dirs-command'. - -Examples: -- \"find %s -type d -name '*%s*'\" -- \"find %s -type d -regex .*%s.*$\" - -*** Insert filename at point or complete filename at point - -On insertion (not on completion, i.e. there is nothing at point): - -- `\\[helm-ff-run-complete-fn-at-point]': insert absolute file name. -- `\\[universal-argument] \\[helm-ff-run-complete-fn-at-point]': insert abbreviated file name. -- `\\[universal-argument] \\[universal-argument] \\[helm-ff-run-complete-fn-at-point]': insert relative file name. -- `\\[universal-argument] \\[universal-argument] \\[universal-argument] \\[helm-ff-run-complete-fn-at-point]': insert basename. - -On completion: - -- Target starts with \"~/\": insert abbreviate file name. -- target starts with \"/\" or \"[a-z]:/\": insert full path. -- Otherwise: insert relative file name. - -*** Use the wildcard to select multiple files - -Use of wilcard is supported to run an action over a set of files. - -Example: You can copy all the files with \".el\" extension by using \"*.el\" and -then run copy action. - -Similarly, \"**.el\" (note the two stars) will recursively select all \".el\" -files under the current directory. - -Note that when recursively copying files, you may have files with same name -dispatched across different subdirectories, so when copying them in the same -directory they will get overwritten. To avoid this Helm has a special action -called \"backup files\" that has the same behavior as the command line \"cp -f ---backup=numbered\": it allows you to copy many files with the same name from -different subdirectories into one directory. Files with same name are renamed -as follows: \"foo.txt.~1~\". Like with the --force option of cp, it is possible -to backup files in current directory. - -This command is available only when `dired-async-mode' is active. - -When using an action that involves an external backend (e.g. grep), using \"**\" -is not recommended (even thought it works fine) because it will be slower to -select all the files. You are better off leaving the backend to do it, it will -be faster. However, if you know you have not many files it is reasonable to use -this, also using not recursive wilcard (e.g. \"*.el\") is perfectly fine for -this. - -The \"**\" feature is active by default in the option `helm-file-globstar'. It -is different from the Bash \"shopt globstar\" feature in that to list files with -a named extension recursively you would write \"**.el\" whereas in Bash it would -be \"**/*.el\". Directory selection with \"**/\" like Bash \"shopt globstar\" -option is not supported yet. - -*** Query replace regexp on filenames - -Replace different parts of a file basename with something else. - -When calling this action you will be prompted twice as with -`query-replace', first for the matching expression of the text to -replace and second for the replacement text. Several facilities, -however, are provided to make the two prompts more powerfull. - -**** Syntax of the first prompt - -In addition to simple regexps, these shortcuts are available: - -- Basename without extension => \"%.\" -- Only extension => \".%\" -- Substring => \"%::\" -- Whole basename => \"%\" - -**** Syntax of the second prompt - -In addition to a simple string to use as replacement, here is what you can use: - -- A placeholder refering to what you have selected in the first prompt: \"\\@\". - -After this placeholder you can use a search-and-replace syntax à-la sed: - - \"\\@/// - -You can select a substring from the string represented by the placeholder: - - \"\\@::\" - -- A special character representing a number which is incremented: \"\\#\". - -- Shortcuts for `upcase', `downcase' and `capitalize' -are available as`%u', `%d' and `%c' respectively. - -**** Examples - -***** Recursively rename all files with \".JPG\" extension to \".jpg\" - -Use the `helm-file-globstar' feature described in [[Use the wildcard to select multiple files][recursive globbing]] -by entering \"**.JPG\" at the end of the Helm-find-files pattern, then hit -\\\\[helm-ff-query-replace-on-filenames]: First \"JPG\", then \"jpg\" -and hit `RET'. - -Alternatively you can enter \".%\" at the first prompt, then \"jpg\" and hit -`RET'. Note that when using this instead of using \"JPG\" at the first prompt, -all extensions will be renamed to \"jpg\" even if the extension of one of the -files is, say, \"png\". If you want to keep the original extension you can use -\"%d\" at the second prompt (downcase). - -***** Batch-rename files from number 001 to 00x - -Use \"\\#\" inside the second prompt. - -Example 1: To rename the files - - foo.jpg - bar.jpg - baz.jpg - -to - - foo-001.jpg - foo-002.jpg - foo-003.jpg - -use \"%.\" as matching regexp and \"foo-\\#\" as replacement string. - -Example 2: To rename the files - - foo.jpg - bar.jpg - baz.jpg - -to - - foo-001.jpg - bar-002.jpg - baz-003.jpg - -use as matching regexp \"%.\" and as replacement string \"\\@-\\#\". - -***** Replace a substring - -Use \"%::\". - -Example: To rename files - - foo.jpg - bar.jpg - baz.jpg - -to - - fOo.jpg - bAr.jpg - bAz.jpg - -use as matching regexp \"%:1:2\" and as replacement string \"%u\" (upcase). - -Note that you \*cannot* use \"%.\" and \".%\" along with substring replacement. - -***** Modify the string from the placeholder (\\@) - -- By substring, i.e. only using the substring of the placeholder: \"\\@::\". -The length of placeholder is used for when unspecified. - -Example 1: \"\\@:0:2\" replaces from the beginning to the second char of the placeholder. - -Example 2: \\@:2: replaces from the second char of the placeholder to the end. - -- By search-and-replace: \"\\@///\". - -Incremental replacement is also handled in . - -Example 3: \"\\@/foo/bar/\" replaces \"foo\" by \"bar\" in the placeholder. - -Example 4: \"\\@/foo/-\\#/\" replaces \"foo\" in the placeholder by 001, 002, etc. - -***** Clash in replacements (avoid overwriting files) - -When performing any of these replacement operations you may end up with same -names as replacement. In such cases Helm numbers the file that would otherwise -overwritten. For instance, should you remove the \"-m\" part from the files -\"emacs-m1.txt\", \"emacs-m2.txt\" and \"emacs-m3.txt\" you would end up with -three files named \"emacs.txt\", the second renaming overwriting first file, and -the third renaming overwriting second file and so on. Instead Helm will -automatically rename the second and third files as \"emacs(1).txt\" and -\"emacs(2).txt\" respectively. - -***** Query-replace on filenames vs. serial-rename action - -Unlike the [[Serial renaming][serial rename]] actions, the files renamed with -the query-replace action stay in their initial directory and are not moved to -the current directory. As such, using \"\\#\" to serial-rename files only makes -sense for files inside the same directory. It even keeps renaming files -with an incremental number in the next directories. - -*** Serial renaming - -You can use the serial-rename actions to rename, copy or symlink marked files to -a specific directory or in the current directory with all the files numbered -incrementally. - -- Serial-rename by renaming: -Rename all marked files with incremental numbering to a specific directory. - -- Serial-rename by copying: -Copy all marked files with incremental numbering to a specific directory. - -- Serial-rename by symlinking: -Symlink all marked files with incremental numbering to a specific directory. - -*** Edit marked files in a dired buffer - -You can open a dired buffer containing only marked files with `\\\\[helm-ff-run-marked-files-in-dired]'. -With a prefix argument you can open this same dired buffer in wdired mode for -editing. Note that wildcards are supported as well, so you can use e.g. -\"*.txt\" to select all \".txt\" files in the current directory or \"**.txt\" to -select all files recursively from the current directory. -See [[Use the wildcard to select multiple files]] section above. - -*** Defining default target directory for copying, renaming, etc - -You can customize `helm-dwim-target' to behave differently depending on the -windows open in the current frame. Default is to provide completion on all -directories associated to each window. - -*** Copying and renaming asynchronously - -If you have the async library installed (if you got Helm from MELPA you do), you -can use it for copying/renaming files by enabling `dired-async-mode'. - -Note that even when async is enabled, running a copy/rename action with a prefix -argument will execute action synchronously. Moreover it will follow the first -file of the marked files in its destination directory. - -When `dired-async-mode' is enabled, an additional action named \"Backup files\" -will be available. (Such command is not natively available in Emacs). -See [[Use the wildcard to select multiple files]] for details. - -*** Bookmark the `helm-find-files' session - -You can bookmark the `helm-find-files' session with `\\[helm-ff-bookmark-set]'. -You can later retrieve these bookmarks by calling `helm-filtered-bookmarks' -or, from the current `helm-find-files' session, by hitting `\\[helm-find-files-toggle-to-bookmark]'. - -*** Grep files from `helm-find-files' - -You can grep individual files from `helm-find-files' by using -\`\\\\[helm-ff-run-grep]'. This same command can also -recursively grep files from the current directory when called with a prefix -argument. In this case you will be prompted for the file extensions to use -\(grep backend) or the types of files to use (ack-grep backend). See the -`helm-grep-default-command' documentation to set this up. For compressed files -or archives, use zgrep with \`\\\\[helm-ff-run-zgrep]'. - -Otherwise you can use recursive commands like \`\\\\[helm-ff-run-grep-ag]' or `\\\\[helm-ff-run-git-grep]' -that are much faster than using `\\\\[helm-ff-run-grep]' with a prefix argument. -See `helm-grep-ag-command' and `helm-grep-git-grep-command' to set this up. - -You can also use \"id-utils\"' GID with \`\\\\[helm-ff-run-gid]' -by creating an ID index file with the \"mkid\" shell command. - -All those grep commands use the symbol at point as the default pattern. -Note that default is different from input (nothing is added to the prompt until -you hit `\\[next-history-element]'). - -**** Grepping on remote files - -On remote files grep is not well supported by TRAMP unless you suspend updates before -entering the pattern and re-enable it once your pattern is ready. -To toggle suspend-update, use `\\\\[helm-toggle-suspend-update]'. - -*** Execute Eshell commands on files - -Setting up aliases in Eshell allows you to set up powerful customized commands. - -Adding Eshell aliases to your `eshell-aliases-file' or using the -`alias' command from Eshell allows you to create personalized -commands not available in `helm-find-files' actions and use them -from `\\\\[helm-ff-run-eshell-command-on-file]'. - -Example: You want a command to uncompress some \"*.tar.gz\" files from `helm-find-files': - -1) Create an Eshell alias named, say, \"untargz\" with the command -\"alias untargz tar zxvf $*\". - -2) Now from `helm-find-files' select the \"*.tar.gz\" file (you can also -mark files if needed) and hit `\\\\[helm-ff-run-eshell-command-on-file]'. - -Note: When using marked files with this, the meaning of the prefix argument is -quite subtle. Say you have \"foo\", \"bar\" and \"baz\" marked; when you run -the alias command `example' on these files with no prefix argument it will run -`example' sequentially on each file: - -$ example foo -$ example bar -$ example baz - -With a prefix argument however it will apply `example' on all files at once: - -$ example foo bar baz - -Of course the alias command should support this. - -If you add %s to the command line %s will be replaced with the candidate, this mean you can -add extra argument to your command e.g. command -extra-arg %s or command %s -extra-arg. -If you want to pass many files inside %s, don't forget to use a prefix arg. - -You can also use special placeholders in extra-args, -see the specific info page once you hit `\\\\[helm-ff-run-eshell-command-on-file]'. - -*** Using TRAMP with `helm-find-files' to read remote directories - -`helm-find-files' works fine with TRAMP despite some limitations. - -- Grepping files is not very well supported when used incrementally. -See [[Grepping on remote files]]. - -- Locate does not work on remote directories. - -**** A TRAMP syntax crash course - -Please refer to TRAMP's documentation for more details. - -- Connect to host 192.168.0.4 as user \"foo\": - -/scp:192.168.0.4@foo: - -- Connect to host 192.168.0.4 as user \"foo\" on port 2222: - -/scp:192.168.0.4@foo#2222: - -- Connect to host 192.168.0.4 as root using multihops syntax: - -/ssh:192.168.0.4@foo|sudo:192.168.0.4: - -Note: You can also use `tramp-default-proxies-alist' when connecting often to -the same hosts. - -As a rule of thumb, prefer the scp method unless using multihops (which only -works with the ssh method), especially when copying large files. - -You need to hit `C-j' once on top of a directory on the first connection -to complete the pattern in the minibuffer. - -**** Display color for directories, symlinks etc... with tramp - -Starting at helm version 2.9.7 it is somewhat possible to -colorize fnames by listing files without loosing performances with -external commands (ls and awk) if your system is compatible. -For this you can use `helm-list-dir-external' as value -for `helm-list-directory-function'. - -See `helm-list-directory-function' documentation for more infos. - -**** Completing host - -As soon as you enter the first \":\" after method e.g =/scp:= you will -have some completion about previously used hosts or from your =~/.ssh/config= -file, hitting `\\[helm-execute-persistent-action]' or `right' on a candidate will insert this host in minibuffer -without addind the ending \":\", second hit insert the last \":\". -As soon the last \":\" is entered TRAMP will kick in and you should see the list -of candidates soon after. - -When connection fails, be sure to delete your TRAMP connection with M-x -`helm-delete-tramp-connection' before retrying. - -**** Editing local files as root - -Use the sudo method: - -\"/sudo:host:\" or simply \"/sudo::\". - -*** Attach files to a mail buffer (message-mode) - -If you are in a `message-mode' or `mail-mode' buffer, that action will appear -in action menu, otherwise it is available at any time with \\\\[helm-ff-run-mail-attach-files]. -It behaves as follows: - -- If you are in a (mail or message) buffer, files are attached there. - -- If you are not in a mail buffer but one or more mail buffers exist, you are -prompted to attach files to one of these mail buffers. - -- If you are not in a mail buffer and no mail buffer exists, -a new mail buffer is created with the attached files in it. - -*** Open files in separate windows - -When [[Marked candidates][marking]] multiple files or using [[Use the wildcard to select multiple files][wildcard]], helm allow opening all -this files in separate windows using an horizontal layout or a -vertical layout if you used a prefix arg, when no more windows can be -displayed in frame, next files are opened in background without being -displayed. When using \\\\[helm-ff-run-switch-other-window] the current -buffer is kept and files are displayed next to it with same behavior as above. -When using two prefix args, files are opened in background without beeing displayed. - -*** Expand archives as directories in a avfs directory - -If you have mounted your filesystem with mountavfs, -you can expand archives in the \"~/.avfs\" directory with \\\\[helm-execute-persistent-action]. - -*** Tramp archive support (emacs-27+ only) - -If your emacs have library tramp-archive.el, you can browse the -content of archives with emacs and BTW helm-find-files. However this beeing -experimental and not very fast, helm doesn't provide an automatic -expansion and detection of archives, you will have to add the final / -manually and may have to force update (\\\\[helm-refresh]) -or remove and add again the final / until tramp finish decompressing archive. - -*** Touch files - -In the completion buffer, you can choose the default which is the current-time, it is -the first candidate or the timestamp of one of the selected files. -If you need to use something else, use \\\\[next-history-element] and edit -the date in minibuffer. -It is also a way to quickly create a new file without opening a buffer, saving it -and killing it. -To touch more than one new file, separate you filenames with a comma (\",\"). -If one wants to create (touch) a new file with comma inside the name use a prefix arg, -this will prevent splitting the name and create multiple files. - -*** Delete files - -You can delete files without quitting helm with -`\\\\[helm-ff-persistent-delete]' or delete files and quit helm with `\\[helm-ff-run-delete-file]'. - -In the second method you can choose to -make this command asynchronous by customizing -\`helm-ff-delete-files-function'. - -_WARNING_: When deleting files asynchronously you will NOT be -WARNED if directories are not empty, that's mean non empty directories will -be deleted in background without asking. - -A good compromise is to trash your files -when using asynchronous method (see [[Trashing files][Trashing files]]). - -When choosing synchronous delete, you can allow recursive -deletion of directories with `helm-ff-allow-recursive-deletes'. -Note that when trashing (synchronous) you are not asked for recursive deletion. - -Note that `helm-ff-allow-recursive-deletes' have no effect when -deleting asynchronously. - -First method (persistent delete) is always synchronous. - -Note that when a prefix arg is given, trashing behavior is inversed. -See [[Trashing files][Trashing files]]. - -**** Trashing files - -If you want to trash your files instead of deleting them you can -set `delete-by-moving-to-trash' to non nil, like this your files -will be moved to trash instead of beeing deleted. - -You can reverse at any time the behavior of `delete-by-moving-to-trash' by using -a prefix arg with any of the delete files command. - -On GNULinux distributions, when navigating to a Trash directory you -can restore any file in ..Trash/files directory with the 'Restore -from trash' action you will find in action menu (needs the -trash-cli package installed for remote files, see [[Trashing remote files with tramp][Here]]). -You can as well delete files from Trash directories with the 'delete files from trash' -action. -If you want to know where a file will be restored, hit `M-i', you will find a trash info. - -Tip: Navigate to your Trash/files directories with `helm-find-files' and set a bookmark -there with \\\\[helm-ff-bookmark-set] for fast access to Trash. - -NOTE: Restoring files from trash is working only on system using -the [[http://freedesktop.org/wiki/Specifications/trash-spec][freedesktop trash specifications]]. - -_WARNING:_ - -If you have an ENV var XDG_DATA_HOME in your .profile or .bash_profile -and this var is set to something like $HOME/.local/share (like preconized) -`move-file-to-trash' may try to create $HOME/.local/share/Trash (literally) -and its subdirs in the directory where you are actually trying to trash files. -because `move-file-to-trash' is interpreting XDG_DATA_HOME literally instead -of evaling its value (with `substitute-in-file-name'). - -***** Trashing remote files with tramp - -Trashing remote files (or local files with sudo method) is disabled by default -because tramp is requiring the 'trash' command to be installed, if you want to -trash your remote files, customize `helm-trash-remote-files'. -The package on most GNU/Linux based distributions is trash-cli, it is available [[https://github.com/andreafrancia/trash-cli][here]]. - -NOTE: -When deleting your files with sudo method, your trashed files will not be listed -with trash-list until you log in as root. - -*** Checksum file - -Checksum is calculated with the md5sum, sha1sum, sha224sum, -sha256sum, sha384sum and sha512sum when available, otherwise the -Emacs function `secure-hash' is used but it is slow and may crash -Emacs and even the whole system as it eats all memory. So if -your system doesn't have the md5 and sha command line tools be -careful when checking sum of larges files e.g. isos. - -*** Ignored or boring files - -Helm-find-files can ignore files matching -`helm-boring-file-regexp-list' or files that are git ignored, you -can set this with `helm-ff-skip-boring-files' or -`helm-ff-skip-git-ignored-files'. - -** Commands -\\ -\\[helm-ff-run-locate]\t\tRun `locate' (`\\[universal-argument]' to specify locate database, `M-n' to insert basename of candidate). -\\[helm-ff-run-browse-project]\t\tBrowse project (`\\[universal-argument]' to recurse, `\\[universal-argument] \\[universal-argument]' to recurse and refresh database). -\\[helm-ff-run-find-sh-command]\t\tRun `find' shell command from this directory. -\\[helm-ff-run-grep]\t\tRun Grep (`\\[universal-argument]' to recurse). -\\[helm-ff-run-pdfgrep]\t\tRun Pdfgrep on marked files. -\\[helm-ff-run-zgrep]\t\tRun zgrep (`\\[universal-argument]' to recurse). -\\[helm-ff-run-grep-ag]\t\tRun AG grep on current directory. -\\[helm-ff-run-git-grep]\t\tRun git-grep on current directory. -\\[helm-ff-run-gid]\t\tRun gid (id-utils). -\\[helm-ff-run-etags]\t\tRun Etags (`\\[universal-argument]' to use thing-at-point, `\\[universal-argument] \\[universal-argument]' to reload cache). -\\[helm-ff-run-rename-file]\t\tRename Files (`\\[universal-argument]' to follow). -\\[helm-ff-run-query-replace-fnames-on-marked]\t\tQuery replace on marked files. -\\[helm-ff-run-copy-file]\t\tCopy Files (`\\[universal-argument]' to follow). -\\[helm-ff-run-byte-compile-file]\t\tByte Compile Files (`\\[universal-argument]' to load). -\\[helm-ff-run-load-file]\t\tLoad Files. -\\[helm-ff-run-symlink-file]\t\tSymlink Files. -\\[helm-ff-run-hardlink-file]\t\tHardlink files. -\\[helm-ff-run-relsymlink-file]\t\tRelative symlink Files. -\\[helm-ff-run-delete-file]\t\tDelete Files. -\\[helm-ff-run-touch-files]\t\tTouch files. -\\[helm-ff-run-kill-buffer-persistent]\t\tKill buffer candidate without leaving Helm. -\\[helm-ff-persistent-delete]\t\tDelete file without leaving Helm. -\\[helm-ff-run-switch-to-eshell]\t\tSwitch to Eshell. -\\[helm-ff-run-eshell-command-on-file]\t\tEshell command on file (`\\[universal-argument]' to apply on marked files, otherwise treat them sequentially). -\\[helm-ff-run-ediff-file]\t\tEdiff file. -\\[helm-ff-run-ediff-merge-file]\t\tEdiff merge file. -\\[helm-ff-run-complete-fn-at-point]\t\tComplete file name at point. -\\[helm-ff-run-switch-other-window]\t\tSwitch to other window. -\\[helm-ff-run-switch-other-frame]\t\tSwitch to other frame. -\\[helm-ff-run-open-file-externally]\t\tOpen file with external program (`\\[universal-argument]' to choose). -\\[helm-ff-run-preview-file-externally]\t\tPreview file with external program. -\\[helm-ff-run-open-file-with-default-tool]\t\tOpen file externally with default tool. -\\[helm-ff-rotate-left-persistent]\t\tRotate image left. -\\[helm-ff-rotate-right-persistent]\t\tRotate image right. -\\[helm-find-files-up-one-level]\t\tGo to parent directory. -\\[helm-find-files-history]\t\tSwitch to the visited-directory history. -\\[helm-ff-file-name-history]\t\tSwitch to file name history. -\\[helm-ff-properties-persistent]\t\tShow file properties in a tooltip. -\\[helm-mark-all]\t\tMark all visible candidates. -\\[helm-ff-run-toggle-auto-update]\t\tToggle auto-expansion of directories. -\\[helm-unmark-all]\t\tUnmark all candidates, visible and invisible ones. -\\[helm-ff-run-mail-attach-files]\t\tAttach files to message buffer. -\\[helm-ff-run-print-file]\t\tPrint file, (`\\[universal-argument]' to refresh printer list). -\\[helm-enlarge-window]\t\tEnlarge Helm window. -\\[helm-narrow-window]\t\tNarrow Helm window. -\\[helm-ff-run-toggle-basename]\t\tToggle basename/fullpath. -\\[helm-ff-run-find-file-as-root]\t\tFind file as root. -\\[helm-ff-run-find-alternate-file]\t\tFind alternate file. -\\[helm-ff-run-insert-org-link]\t\tInsert org link. -\\[helm-ff-bookmark-set]\t\tSet bookmark to current directory. -\\[helm-find-files-switch-to-bookmark]\t\tJump to bookmark list. -\\[helm-ff-sort-alpha]\t\tSort alphabetically -\\[helm-ff-sort-by-newest]\t\tSort by newest -\\[helm-ff-sort-by-size]\t\tSort by size") - -;;; Help for file-name-history -;; -;; -(defvar helm-file-name-history-help-message - "* Helm file name history - -** Tips -You can open directly the selected file and exit helm or preselect the file in helm-find-files, -see actions in action menu. - -You can toggle the view of deleted files, see commands below. - -** Commands -\\ -\\[helm-file-name-history-show-or-hide-deleted]\t\tToggle deleted files view.") - -;;; Help for `helm-read-file-name' -;; -;; -(defun helm-read-file-name-help-message () - (let ((name (if helm-alive-p - (assoc-default 'name (helm-get-current-source)) - "generic"))) - (format - "* Helm `%s' read file name completion - -This is `%s' read file name completion that have been \"helmized\" -because you have enabled [[Helm mode][helm-mode]]'. -Don't confuse this with `helm-find-files' which is a native helm command, -see [[Helm functions vs helmized Emacs functions]]. - -** Tips - -*** Navigation - -**** Enter `~/' at end of pattern to quickly reach home directory - -**** Enter `/' at end of pattern to quickly reach the file system root - -**** Enter `./' at end of pattern to quickly reach `default-directory' - -\(As per its value at the beginning of the session.) - -If you already are in the `default-directory' this will move the cursor to the top. - -**** Enter `../' at end of pattern will reach upper directory, moving cursor on top - -This is different from using `\\[helm-find-files-up-one-level]' in that it moves -the cursor to the top instead of remaining on the previous subdir name. - -**** You can complete with partial basename - -It starts from the third character of the pattern. - -For instance \"fob\" or \"fbr\" will complete \"foobar\" but \"fb\" needs a -third character in order to complete it. - -*** Persistent actions - -By default `helm-read-file-name' uses the persistent actions of `helm-find-files'. - -**** Use `\\[universal-argument] \\\\[helm-execute-persistent-action]' to display an image - -**** `\\\\[helm-execute-persistent-action]' on a filename will expand to this filename in Helm-buffer - -Second hit displays the buffer filename. -Third hit kills the buffer filename. -Note: `\\[universal-argument] \\\\[helm-execute-persistent-action]' displays the buffer directly. - -**** Browse images directories with `helm-follow-mode' and navigate up/down - -*** Delete characters backward - -When you want to delete characters backward, e.g. to create a new file or directory, -auto-update may come in the way when it keeps updating to an existent directory. -In that case, type `C-' and then `'. -This should not be needed when copying/renaming files because autoupdate is disabled -by default in that case. - -Note: On a terminal, the default binding `C-' may not work. -In this case use `C-c '. - -*** Create new directories and files - -**** You can create a new directory and a new file at the same time - -Simply write the path in prompt and press `RET', e.g. -\"~/new/newnew/newnewnew/my_newfile.txt\". - -**** To create a new directory, append a \"/\" at to the new name and press `RET' - -**** To create a new file, enter a filename not ending with \"/\" - -File and directory creation works only with some commands (e.g. `find-file') -and it will not work with others where it is not intended to return a file or -a directory \(e.g `list-directory'). - -*** Exiting minibuffer with empty string - -You can exit minibuffer with empty string with \\\\[helm-cr-empty-string]. -It is useful when some commands are prompting continuously until you enter an empty prompt. - -** Commands -\\ -\\[helm-find-files-up-one-level]\t\tGo to parent directory. -\\[helm-ff-run-toggle-auto-update]\t\tToggle auto-expansion of directories. -\\[helm-ff-run-toggle-basename]\t\tToggle basename. -\\[helm-ff-file-name-history]\t\tFile name history. -C/\\[helm-cr-empty-string]\t\tReturn empty string unless `must-match' is non-nil. -\\[helm-next-source]\t\tGo to next source. -\\[helm-previous-source]\t\tGo to previous source." - name name))) - -;;; Generic file help - Used by locate. -;; -;; -(defvar helm-generic-file-help-message - "* Helm Generic files - -** Tips - -*** Locate - -You can append to the search pattern any of the locate command line options, -e.g. -b, -e, -n , etc. See the locate(1) man page for more details. - -Some other sources (at the moment \"recentf\" and \"file in current directory\") -support the -b flag for compatibility with locate when they are used with it. - -When you enable fuzzy matching on locate with `helm-locate-fuzzy-match', the -search will be performed on basename only for efficiency (so don't add \"-b\" at -prompt). As soon as you separate the patterns with spaces, fuzzy matching will -be disabled and search will be done on the full filename. Note that in -multi-match, fuzzy is completely disabled, which means that each pattern is a -match regexp (i.e. \"helm\" will match \"helm\" but \"hlm\" will \*not* match -\"helm\"). - -*** Browse project - -When the current directory is not under version control, don't forget to refresh -the cache when files have been added/removed in the directory. - -*** Find command - -Recursively search files using the \"find\" shell command. - -Candidates are all filenames that match all given globbing patterns. This -respects the options `helm-case-fold-search' and -`helm-findutils-search-full-path'. - -You can pass arbitrary \"find\" options directly after a \"*\" separator. -For example, this would find all files matching \"book\" that are larger -than 1 megabyte: - - book * -size +1M - -** Commands -\\ -\\[helm-ff-run-toggle-basename]\t\tToggle basename. -\\[helm-ff-run-grep]\t\tRun grep (`\\[universal-argument]' to recurse). -\\[helm-ff-run-zgrep]\t\tRun zgrep. -\\[helm-ff-run-gid]\t\tRun GID (id-utils). -\\[helm-ff-run-pdfgrep]\t\tRun PDFgrep on marked files. -\\[helm-ff-run-copy-file]\t\tCopy file(s) -\\[helm-ff-run-rename-file]\t\tRename file(s). -\\[helm-ff-run-symlink-file]\t\tSymlink file(s). -\\[helm-ff-run-hardlink-file]\t\tHardlink file(s). -\\[helm-ff-run-delete-file]\t\tDelete file(s). -\\[helm-ff-run-byte-compile-file]\t\tByte compile Elisp file(s) (`\\[universal-argument]' to load). -\\[helm-ff-run-load-file]\t\tLoad Elisp file(s). -\\[helm-ff-run-ediff-file]\t\tEdiff file. -\\[helm-ff-run-ediff-merge-file]\t\tEdiff-merge file. -\\[helm-ff-run-switch-other-window]\t\tSwitch to other window. -\\[helm-ff-properties-persistent]\t\tShow file properties. -\\[helm-ff-run-etags]\t\tRun etags (`\\[universal-argument]' to use tap, `\\[universal-argument] \\[universal-argument]' to reload the database). -\\[helm-ff-run-open-file-externally]\t\tOpen file with external program (`\\[universal-argument]' to choose). -\\[helm-ff-run-open-file-with-default-tool]\t\tOpen file externally with default tool. -\\[helm-ff-run-insert-org-link]\t\tInsert org link.") - -;;; Grep help -;; -;; -(defvar helm-grep-help-message - "* Helm Grep - -** Tips - -*** Use a prefix argument to grep recursively - -With Helm supporting git-grep and AG however, you are better off using one of -them for recursive searches. - -*** You can use wild cards when selecting files (e.g. \"*.el\") - -*** You can grep in many different directories by marking files or using wild cards - -*** You can save the result in a `helm-grep-mode' buffer - -See [[Commands][commands]] below. - -Once in that buffer you can use \"emacs-wgrep\" (external package not bundled with Helm) -to edit your changes. - -*** Helm-grep supports multi-matching - -\(Starting from version 1.9.4.) - -Simply add a space between each pattern as for most Helm commands. - -*** See full path of selected candidate - -Add (helm-popup-tip-mode 1) in your init file or enable it interactively with -M-x helm-popup-tip-mode. - -*** Open file in other window - -The command \\\\[helm-grep-run-other-window-action] allow you to open file -in other window horizontally or vertically if a prefix arg is supplied. - -*** Performance over TRAMP - -Grepping works but it is badly supported as TRAMP doesn't support multiple -processes running in a short delay (less than 5s) among other things. - -Helm uses a special hook to suspend the process automatically while you are -typing. Even if Helm handles this automatically by delaying each process by 5s, -you are adviced to this manually by hitting `\\\\[helm-toggle-suspend-update]' (suspend process) before -typing, and hit again `\\\\[helm-toggle-suspend-update]' when the regexp is ready to send to the remote -process. For simple regexps, there should be no need for this. - -Another solution is to not use TRAMP at all and mount your remote file system via -SSHFS. - -* Helm GID - -** Tips - -Helm-GID reads the database created with the `mkid' command from id-utils. -The name of the database file can be customized with `helm-gid-db-file-name', it -is usually \"ID\". - -Helm-GID use the symbol at point as default-input. This command is also -accessible from `helm-find-files' which allow you to navigate to another -directory to consult its database. - -Note: Helm-GID supports multi-matches but only the last pattern entered will be -highlighted since there is no ~--color~-like option in GID itself. - -* Helm AG - -** Tips - -Helm-AG is different from grep or ack-grep in that it works on a directory and -not on a list of files. - -You can ignore files and directories with a \".agignore\" file, local to a -directory or global when placed in the home directory. \(See the AG man page for -more details.) That file follows the same syntax as `helm-grep-ignored-files' -and `helm-grep-ignored-directories'. - -As always you can access Helm AG from `helm-find-files'. - -Starting with version 0.30, AG accepts one or more TYPE arguments on its command -line. Helm provides completion on these TYPE arguments when available with your -AG version. Use a prefix argument when starting a Helm-AG session to enable this -completion. - -Note: You can mark several types to match in the AG query. The first AG -versions providing this feature allowed only one type, so in this case only the -last mark will be used. - -* Helm git-grep - -Helm-git-grep searches the current directory, i.e the default directory or the -directory in Helm-find-files. If this current directory is a subdirectory of a -project and you want to also match parent directories (i.e the whole project), -use a prefix argument. - -** Commands -\\ -\\[helm-goto-next-file]\t\tNext File. -\\[helm-goto-precedent-file]\t\tPrevious File. -\\[helm-yank-text-at-point]\t\tYank text at point in minibuffer. -\\[helm-grep-run-other-window-action]\t\tJump to other window. -\\[helm-grep-run-other-frame-action]\t\tJump to other frame. -\\[helm-grep-run-default-action]\t\tRun default action (same as `RET'). -\\[helm-grep-run-save-buffer]\t\tSave to a `helm-grep-mode' enabled buffer.") - -;;; PDF grep help -;; -;; -(defvar helm-pdfgrep-help-message - "* Helm PDFgrep Map - -** Commands -\\ -\\[helm-goto-next-file]\t\tNext file. -\\[helm-goto-precedent-file]\t\tPrevious file. -\\[helm-yank-text-at-point]\t\tYank text at point in minibuffer.") - -;;; Etags help -;; -;; -(defvar helm-etags-help-message - "* Helm Etags Map - -** Commands -\\ -\\[helm-goto-next-file]\t\tNext file. -\\[helm-goto-precedent-file]\t\tPrevious file. -\\[helm-yank-text-at-point]\t\tYank text at point in minibuffer.") - -;;; UCS help -;; -;; -(defvar helm-ucs-help-message - "* Helm UCS - -** Tips - -Use commands below to insert unicode characters in current buffer without -leaving Helm. - -** Commands -\\ -\\[helm-ucs-persistent-insert]\t\tInsert character. -\\[helm-ucs-persistent-forward]\t\tForward character. -\\[helm-ucs-persistent-backward]\t\tBackward character. -\\[helm-ucs-persistent-delete]\t\tDelete character backward. -\\[helm-ucs-persistent-insert-space]\t\tInsert space.") - -;;; Bookmark help -;; -;; -(defvar helm-bookmark-help-message - "* Helm bookmark name - -** Commands -\\ -\\[helm-bookmark-run-jump-other-window]\t\tJump other window. -\\[helm-bookmark-run-delete]\t\tDelete bookmark. -\\[helm-bookmark-run-edit]\t\tEdit bookmark. -\\[helm-bookmark-toggle-filename]\t\tToggle bookmark location visibility.") - -;;; Eshell command on file help -;; -;; -(defvar helm-esh-help-message - "* Helm Eshell on file - -** Tips - -*** Pass extra arguments after filename - -Normally the command or alias will be called with file as argument. For instance - - candidate_file - -But you can also pass an argument or more after \"candidate_file\" like this: - - %s [extra_args] - -\"candidate_file\" will be added at \"%s\" and the command will look at this: - - candidate_file [extra_args] - -**** Use placeholders in extra arguments - -placeholder for file without extension: \\@ -placeholder for incremental number: \\# - -\"candidate_file\" will be added at \"%s\" and \\@ but without extension. - - - -\"candidate_file\" will be added at \"%s\" and \\# will be replaced by an incremental number. - - %s \\# - -Here examples: - -Say you want to use the =convert= command to convert all your .png files in a directory to .jpg. - -This will convert all your files to jpg keeping the same basename. - - convert %s \\@.jpg - -This will convert all your files to foo-001.jpg, foo-002.jpg etc... - - convert %s foo-\\#.jpg - -You can of course combine both placeholders if needed. - - convert %s \\@-\\#.jpg - -*** Specify marked files as arguments - -Example: - - file1 file2... - -Call `helm-find-files-eshell-command-on-file' with one prefix argument. Otherwise -you can pass one prefix argument from the command selection buffer. - -Note: This does not work on remote files. - -With two prefix-args the output is printed to the `current-buffer'. - -With no prefix argument or a prefix argument value of '(16) (`\\[universal-argument] \\[universal-argument]') -the command is called once for each file like this: - - file1 - file2 - ... - -** Commands -\\") - -;;; Ido virtual buffer help -;; -;; -(defvar helm-buffers-ido-virtual-help-message - "* Helm Ido virtual buffers - -** Commands -\\ -\\[helm-ff-run-switch-other-window]\t\tSwitch to other window. -\\[helm-ff-run-switch-other-frame]\t\tSwitch to other frame. -\\[helm-ff-run-grep]\t\tGrep file. -\\[helm-ff-run-zgrep]\t\tZgrep file. -\\[helm-ff-run-delete-file]\t\tDelete file. -\\[helm-ff-run-open-file-externally]\t\tOpen file externally.") - -;;; Moccur help -;; -;; -(defvar helm-moccur-help-message - "* Helm Moccur - -** Tips - -*** Matching - -Multiple regexp matching is allowed, simply enter a space to separate the regexps. - -Matching empty lines is supported with the regexp \"^$\", you then get the -results displayed as the buffer-name and the line number only. You can -save and edit these results, i.e. add text to the empty line. - -*** Automatically match symbol at point - -Helm can automatically match the symbol at point while keeping the minibuffer -empty, ready to be written to. This behaviour is disabled by default. To -enable this you need to add `helm-source-occur' and `helm-source-moccur' to -`helm-sources-using-default-as-input'. - -*** Jump to the corresponding line in the searched buffer - -You can do this with `\\\\[helm-execute-persistent-action]' (persistent-action), to do it repeatedly -you can use `\\\\[helm-follow-action-forward]' and `\\\\[helm-follow-action-backward]' or enable `helm-follow-mode' with `\\\\[helm-follow-mode]'. -Follow mode is enabled by default in helm-occur. - -*** Switch to buffer in other window - -The command \\\\[helm-moccur-run-goto-line-ow] allow you to switch to buffer -in other window horizontally or vertically if a prefix arg is supplied. - -*** Save the results - -Similarly to Helm-grep, you can save the results with `\\\\[helm-occur-run-save-buffer]'. -Once in the saved buffer, you can edit it, see [[Edit a saved buffer][below]]. - -Of course if you don't save the results, you can resume the Helm session with -`helm-resume'. - -*** Refresh the resumed session - -When the buffer(s) where you ran helm-(m)occur get(s) modified, the Helm buffer -will flash red as a warning. You can refresh the buffer by running `\\\\[helm-refresh]'. -This can be done automatically by customizing `helm-moccur-auto-update-on-resume'. - -*** Refresh a saved buffer - -Type `g' to update the buffer. - -*** Edit a saved buffer - -First, install wgrep (https://github.com/mhayashi1120/Emacs-wgrep) and then: - -1) `C-c C-p' (`wgrep-change-to-wgrep-mode') to edit the buffer(s). -2) `C-x C-s' to save your changes. - -Tip: Use the excellent iedit (https://github.com/victorhge/iedit) to modify all -occurences at once in the buffer. - -*** Search in region - -When searching in current-buffer with `helm-occur', if a region -is found helm will search in this region only. If you marked -this region with `mark-defun' the symbol that was at point before -marking defun will be used when `helm-source-occur' is member of -`helm-sources-using-default-as-input'. - -*** Switch to next or previous source - -See [[Moving in `helm-buffer'][Moving in `helm-buffer']]. - -** Commands -\\ -\\[helm-occur-run-goto-line-ow]\t\tGo to line in other window. -\\[helm-occur-run-goto-line-of]\t\tGo to line in new frame. -\\[helm-occur-run-save-buffer]\t\tSave results in new buffer.") -;;; Helm Top -;; -;; -(defvar helm-top-help-message - "* Helm Top - -** Commands -\\ -\\[helm-top-run-sort-by-com]\t\tSort by commands. -\\[helm-top-run-sort-by-cpu]\t\tSort by CPU usage. -\\[helm-top-run-sort-by-user]\t\tSort alphabetically by user. -\\[helm-top-run-sort-by-mem]\t\tSort by memory.") - -;;; Helm Elisp package -;; -;; -(defvar helm-el-package-help-message - "* Helm Elisp package - -** Tips - -*** Compile all your packages asynchronously - -If you use async (if you have installed Helm from MELPA you do), only \"helm\", -\"helm-core\", and \"magit\" are compiled asynchronously. If you want all your -packages compiled asynchronously, add this to your init file: - - (setq async-bytecomp-allowed-packages '(all)) - -*** Upgrade Elisp packages - -On initialization (when Emacs is fetching packages on remote), if Helm finds -packages to upgrade, it will start in the upgradable packages view showing the packages -available for upgrade. - -On subsequent runs, you will have to refresh the list with `C-c \\[universal-argument]'. If Helm -finds upgrades you can switch to upgrade view (see below) to see what packages -are available for upgrade or simply hit `C-c U' to upgrade them all. - -To see upgradable packages hit `M-U'. - -Then you can install all upgradable packages with the \"upgrade all\" action -\(`C-c \\[universal-argument]'), or upgrade only specific packages by marking them and running the -\"upgrade\" action (visible only when there are upgradable packages). Of course -you can upgrade a single package by just running the \"upgrade\" action without -marking it (`C-c u' or `RET') . - -\*Warning:* You are strongly advised to \*restart* Emacs after \*upgrading* packages. - -*** Meaning of flags prefixing packages - -\(Emacs ≥25) - -- The flag \"S\" that prefixes package names means that the packages belong to `package-selected-packages'. - -- The flag \"U\" that prefix package names mean that this package is no more needed. - -** Commands -\\ -\\[helm-el-package-show-all]\t\tShow all packages. -\\[helm-el-package-show-installed]\t\tShow installed packages only. -\\[helm-el-package-show-uninstalled]\t\tShow non-installed packages only. -\\[helm-el-package-show-upgrade]\t\tShow upgradable packages only. -\\[helm-el-package-show-built-in]\t\tShow built-in packages only. -\\[helm-el-run-package-install]\t\tInstall package(s). -\\[helm-el-run-package-reinstall]\t\tReinstall package(s). -\\[helm-el-run-package-uninstall]\t\tUninstall package(s). -\\[helm-el-run-package-upgrade]\t\tUpgrade package(s). -\\[helm-el-run-package-upgrade-all]\t\tUpgrade all packages. -\\[helm-el-run-visit-homepage]\t\tVisit package homepage.") - -;;; Helm M-x -;; -;; -(defvar helm-M-x-help-message - "* Helm M-x - -** Tips - -*** You can get help on any command with persistent action (\\[helm-execute-persistent-action]) - -*** Prefix arguments - -You must pass prefix arguments \*after* starting `helm-M-x'. A mode-line -counter will display the number of given prefix arguments. - -If you pass prefix arguments before running `helm-M-x', it will be displayed in the prompt. -The first `\\[universal-argument]' after `helm-M-x' clears those prefix arguments.") - -;;; Helm imenu -;; -;; -(defvar helm-imenu-help-message - "* Helm Imenu - -** Commands -\\ -\\[helm-imenu-next-section]\t\tGo to next section. -\\[helm-imenu-previous-section]\t\tGo to previous section.") - -;;; Helm colors -;; -;; -(defvar helm-colors-help-message - "* Helm colors - -** Commands -\\ -\\[helm-color-run-insert-name]\t\tInsert the entry name. -\\[helm-color-run-kill-name]\t\tKill the entry name. -\\[helm-color-run-insert-rgb]\t\tInsert entry in RGB format. -\\[helm-color-run-kill-rgb]\t\tKill entry in RGB format.") - -;;; Helm Semantic -;; -;; -(defvar helm-semantic-help-message - "* Helm Semantic - -** Commands -\\") - -;;; Helm kmacro -;; -;; -(defvar helm-kmacro-help-message - "* Helm kmacro - -** Tips - -- Start recording a kmacro with `f3'. -- End the kmacro recording with `f4'. -- Run `helm-execute-kmacro' to list all your kmacros. - -Use persistent action to run your kmacro as many time as needed. -You can browse the kmacros with `helm-next-line' and `helm-previous-line'. - -Note: You can't record keys running Helm commands except `helm-M-x', under the -condition that you don't choose a command using Helm completion. - -** Commands -\\") - -;;; Kill ring -;; -;; -(defvar helm-kill-ring-help-message - "* Helm kill ring - -** Tips - -Every Helm session lets you save a candidate to the kill-ring / clipboard / -primary-selection with `\\\\[helm-kill-selection-and-quit]'. - -To save space, Helm-kill-ring truncates the candidates longer than -`helm-kill-ring-max-offset'. -`\\\\[helm-kill-ring-kill-selection]' then saves the whole -text and not the truncated value. The view of truncated candidates can be -toggled; see the command list below. - -As opposed to `yank', numeric prefix arguments are ignored with -`helm-show-kill-ring': there is no need for them since selection happens within -Helm. Moreover Helm has [[Shortcuts for executing the default action on the n-th candidate][Shortcuts for executing the default action on the n-th candidate]]. - -It is recommended to globally bind `M-y' to `helm-show-kill-ring'. Once in the -Helm-kill-ring session you can navigate to next/previous line with `M-y' and -`M-u' for convenience. Of course `\\[helm-next-line]' and `\\[helm-previous-line]' are still available. - -It is possible to delete candidates from the kill ring with `\\\\[helm-kill-ring-delete]' -but also persistently with `\\\\[helm-kill-ring-run-persistent-delete]'. - -You can concatenate marked candidates and yank them in the current -buffer, thus creating a new entry in the kill ring. Candidates are -concatenated with `helm-kill-ring-separator' as default but you can -change interactively the separator while yanking by using two prefix -args. When you have something else than \"\\n\" as default value for -`helm-kill-ring-separator' and you want to use \"\\n\" from prompt, use -`C-q C-j' to enter a newline in prompt. - -To not push a new entry in the kill ring, use `\\\\[helm-copy-to-buffer]' instead of RET -\(note that you can't change separator with this). - -When inserting candidates with the default action (`RET'), `point' is placed at -the end of the candidate and `mark' at the beginning. You can revert this behavior -by using a prefix argument, i.e. `C-u RET', like the regular `yank' command does. - -** Commands -\\ -\\[helm-next-line]\t\tNext line. -\\[helm-previous-line]\t\tPrevious line. -\\[helm-kill-ring-delete]\t\tDelete entry. -\\[helm-kill-ring-toggle-truncated]\t\tToggle truncated view of candidate. -\\[helm-kill-ring-kill-selection]\t\tKill non-truncated of selection.") - -;;; Completing-read -;; -(defun helm-comp-read-help-message () - (let ((com (assoc-default 'name (helm-get-current-source)))) - (format - "* Helm completing-read completion for `%s' - -Command `%s' is using a `completing-read' for completion on your input, -this completion have been \"helmized\" because you have enabled [[Helm mode][helm-mode]]'. - -** Tips - -*** Disabling or use something else than helm for completion of some commands - -You can disable helm completion or use something else for specific commands of your choice, -for this customize variable `helm-completing-read-handlers-alist'. - -*** Exiting minibuffer with empty string - -You can exit minibuffer with empty string with \\\\[helm-cr-empty-string]. -It is useful when some commands are prompting continuously until you enter an empty prompt. - -** Commands -\\ -\\[helm-cr-empty-string]\t\tExit minibuffer with empty string." - com com))) - - -;;; Mode line strings -;; -;; -;;;###autoload -(defvar helm-comp-read-mode-line "\ -\\\ -C/\\[helm-cr-empty-string]:Empty \ -\\\ -\\[helm-help]:Help \ -\\[helm-select-action]:Act \ -\\[helm-maybe-exit-minibuffer]/\ -f1/f2/f-n:NthAct \ -\\[helm-toggle-suspend-update]:Tog.suspend \ -\\[helm-customize-group]:Conf") - -;;;###autoload -(defvar helm-read-file-name-mode-line-string "\ -\\\ -\\[helm-help]:Help \ -C/\\[helm-cr-empty-string]:Empty \ -\\\ -\\[helm-select-action]:Act \ -\\[helm-maybe-exit-minibuffer]/\ -f1/f2/f-n:NthAct \ -\\[helm-toggle-suspend-update]:Tog.suspend \ -\\[helm-customize-group]:Conf" - "String displayed in mode-line in `helm-source-find-files'.") - -;;;###autoload -(defvar helm-top-mode-line "\ -\\\ -\\[helm-help]:Help \ -\\\ -\\[helm-select-action]:Act \ -\\[helm-maybe-exit-minibuffer]/\ -f1/f2/f-n:NthAct \ -\\[helm-toggle-suspend-update]:Tog.suspend \ -\\[helm-customize-group]:Conf") - - -(provide 'helm-help) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-help.el ends here diff --git a/elpa/helm-20191031.725/helm-id-utils.el b/elpa/helm-20191031.725/helm-id-utils.el deleted file mode 100644 index 8752fd55..00000000 --- a/elpa/helm-20191031.725/helm-id-utils.el +++ /dev/null @@ -1,131 +0,0 @@ -;;; helm-id-utils.el --- Helm interface for id-utils. -*- lexical-binding: t -*- - -;; Copyright (C) 2015 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'helm-grep) -(require 'helm-help) - -(defgroup helm-id-utils nil - "ID-Utils related Applications and libraries for Helm." - :group 'helm) - -(defcustom helm-gid-program "gid" - "Name of gid command (usually `gid'). -For Mac OS X users, if you install GNU coreutils, the name `gid' -might be occupied by `id' from GNU coreutils, and you should set -it to correct name (or absolute path), for example, if using -MacPorts to install id-utils, it should be `gid32'." - :group 'helm-id-utils - :type 'file) - -(defcustom helm-gid-db-file-name "ID" - "Name of a database file created by `mkid' command from `ID-utils'." - :group 'helm-id-utils - :type 'string) - -(defun helm-gid-candidates-process () - (let* ((patterns (helm-mm-split-pattern helm-pattern)) - (default-com (format "%s -r %s" helm-gid-program - (shell-quote-argument (car patterns)))) - (cmd (helm-aif (cdr patterns) - (concat default-com - (cl-loop for p in it - concat (format " | grep --color=always %s" - (shell-quote-argument p)))) - default-com)) - (proc (start-process-shell-command - "gid" helm-buffer cmd))) - (set (make-local-variable 'helm-grep-last-cmd-line) cmd) - (prog1 proc - (set-process-sentinel - proc (lambda (_process event) - (when (string= event "finished\n") - (helm-maybe-show-help-echo) - (with-helm-window - (setq mode-line-format - '(" " mode-line-buffer-identification " " - (:eval (format "L%s" (helm-candidate-number-at-point))) " " - (:eval (propertize - (format "[Helm Gid process finished - (%s results)]" - (max (1- (count-lines - (point-min) (point-max))) - 0)) - 'face 'helm-locate-finish)))) - (force-mode-line-update)) - (helm-log "Error: Gid %s" - (replace-regexp-in-string "\n" "" event)))))))) - -(defun helm-gid-filtered-candidate-transformer (candidates _source) - ;; "gid -r" may add dups in some rare cases. - (cl-loop for c in (helm-fast-remove-dups candidates :test 'equal) - collect (helm-grep--filter-candidate-1 c))) - -(defclass helm-gid-source (helm-source-async) - ((header-name - :initform - (lambda (name) - (concat name " [" (helm-attr 'db-dir) "]"))) - (db-dir :initarg :db-dir - :initform nil - :custom string - :documentation " Location of ID file.") - (candidates-process :initform #'helm-gid-candidates-process) - (filtered-candidate-transformer - :initform #'helm-gid-filtered-candidate-transformer) - (candidate-number-limit :initform 99999) - (action :initform (helm-make-actions - "Find File" 'helm-grep-action - "Find file other frame" 'helm-grep-other-frame - "Save results in grep buffer" 'helm-grep-save-results - "Find file other window" 'helm-grep-other-window)) - (persistent-action :initform 'helm-grep-persistent-action) - (history :initform 'helm-grep-history) - (nohighlight :initform t) - (help-message :initform 'helm-grep-help-message) - (requires-pattern :initform 2))) - -;;;###autoload -(defun helm-gid () - "Preconfigured helm for `gid' command line of `ID-Utils'. -Need A database created with the command `mkid' -above `default-directory'. -Need id-utils as dependency which provide `mkid', `gid' etc... -See ." - (interactive) - (let* ((db (locate-dominating-file - default-directory - helm-gid-db-file-name)) - (helm-grep-default-directory-fn - (lambda () default-directory)) - (helm--maybe-use-default-as-input t)) - (cl-assert db nil "No DataBase found, create one with `mkid'") - (helm :sources (helm-make-source "Gid" 'helm-gid-source - :db-dir db) - :buffer "*helm gid*" - :keymap helm-grep-map - :truncate-lines helm-grep-truncate-lines))) - -(provide 'helm-id-utils) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-id-utils ends here diff --git a/elpa/helm-20191031.725/helm-imenu.el b/elpa/helm-20191031.725/helm-imenu.el deleted file mode 100644 index 2ff19723..00000000 --- a/elpa/helm-20191031.725/helm-imenu.el +++ /dev/null @@ -1,367 +0,0 @@ -;;; helm-imenu.el --- Helm interface for Imenu -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'cl-lib) -(require 'helm) -(require 'helm-lib) -(require 'imenu) -(require 'helm-utils) -(require 'helm-help) - - -(defgroup helm-imenu nil - "Imenu related libraries and applications for helm." - :group 'helm) - -(defcustom helm-imenu-delimiter " / " - "Delimit types of candidates and his value in `helm-buffer'." - :group 'helm-imenu - :type 'string) - -(defcustom helm-imenu-execute-action-at-once-if-one - #'helm-imenu--execute-action-at-once-p - "Goto the candidate when only one is remaining." - :group 'helm-imenu - :type 'function) - -(defcustom helm-imenu-all-buffer-assoc nil - "Major mode association alist for `helm-imenu-in-all-buffers'. -Allow `helm-imenu-in-all-buffers' searching in these associated buffers -even if they are not derived from each other. -The alist is bidirectional, i.e no need to add '((foo . bar) (bar . foo)) -only '((foo . bar)) is needed." - :type '(alist :key-type symbol :value-type symbol) - :group 'helm-imenu) - -(defcustom helm-imenu-in-all-buffers-separate-sources t - "Display imenu index of each buffer in its own source when non-nil. - -When nil all candidates are displayed in a single source. - -NOTE: Each source will have as name \"Imenu \". -`helm-source-imenu-all' will not be set, however it will continue -to be used as a flag for using default as input, if you do not want -this behavior, remove it from `helm-sources-using-default-as-input' -even if not using a single source to display imenu in all buffers." - :type 'boolean - :group 'helm-imenu) - -(defcustom helm-imenu-type-faces - '(("^Variables$" . font-lock-variable-name-face) - ("^\\(Function\\|Functions\\|Defuns\\)$" . font-lock-function-name-face) - ("^\\(Types\\|Provides\\|Requires\\|Classes\\|Class\\|Includes\\|Imports\\|Misc\\|Code\\)$" . font-lock-type-face)) - "Faces for showing type in helm-imenu. -This is a list of cons cells. The cdr of each cell is a face to be used, -and it can also just be like \\='(:foreground \"yellow\"). -Each car is a regexp match pattern of the imenu type string." - :group 'helm-faces - :type '(repeat - (cons - (regexp :tag "Imenu type regexp pattern") - (sexp :tag "Face")))) - -(defcustom helm-imenu-extra-modes nil - "Extra modes where helm-imenu-in-all-buffers should look into." - :group 'helm-imenu - :type '(repeat symbol)) - -;;; keymap -(defvar helm-imenu-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "M-") 'helm-imenu-next-section) - (define-key map (kbd "M-") 'helm-imenu-previous-section) - map)) - -(defcustom helm-imenu-lynx-style-map nil - "Use Arrow keys to jump to occurences." - :group 'helm-imenu - :type 'boolean - :set (lambda (var val) - (set var val) - (if val - (progn - (define-key helm-imenu-map (kbd "") 'helm-execute-persistent-action) - (define-key helm-imenu-map (kbd "") 'helm-maybe-exit-minibuffer)) - (define-key helm-imenu-map (kbd "") nil) - (define-key helm-imenu-map (kbd "") nil)))) - -(defun helm-imenu-next-or-previous-section (n) - (with-helm-window - (let* ((fn (lambda () - (car (split-string - (buffer-substring - (point-at-bol) (point-at-eol)) - helm-imenu-delimiter)))) - (curtype (funcall fn)) - (stop-fn (if (> n 0) - #'helm-end-of-source-p - #'helm-beginning-of-source-p))) - (while (and (not (funcall stop-fn)) - (string= curtype (funcall fn))) - (forward-line n)) - (helm-mark-current-line) - (helm-follow-execute-persistent-action-maybe)))) - -(defun helm-imenu-next-section () - (interactive) - (helm-imenu-next-or-previous-section 1)) - -(defun helm-imenu-previous-section () - (interactive) - (helm-imenu-next-or-previous-section -1)) - - -;;; Internals -(defvar helm-cached-imenu-alist nil) -(make-variable-buffer-local 'helm-cached-imenu-alist) - -(defvar helm-cached-imenu-candidates nil) -(make-variable-buffer-local 'helm-cached-imenu-candidates) - -(defvar helm-cached-imenu-tick nil) -(make-variable-buffer-local 'helm-cached-imenu-tick) - -(defvar helm-imenu--in-all-buffers-cache nil) - -(defvar helm-source-imenu nil "See (info \"(emacs)Imenu\")") -(defvar helm-source-imenu-all nil) - -(defclass helm-imenu-source (helm-source-sync) - ((candidates :initform 'helm-imenu-candidates) - (candidate-transformer :initform 'helm-imenu-transformer) - (persistent-action :initform 'helm-imenu-persistent-action) - (persistent-help :initform "Show this entry") - (nomark :initform t) - (keymap :initform helm-imenu-map) - (help-message :initform 'helm-imenu-help-message) - (action :initform 'helm-imenu-action) - (group :initform 'helm-imenu))) - -(defcustom helm-imenu-fuzzy-match nil - "Enable fuzzy matching in `helm-source-imenu'." - :group 'helm-imenu - :type 'boolean - :set (lambda (var val) - (set var val) - (setq helm-source-imenu - (helm-make-source "Imenu" 'helm-imenu-source - :fuzzy-match helm-imenu-fuzzy-match)))) - -(defun helm-imenu--maybe-switch-to-buffer (candidate) - (let ((cand (cdr candidate))) - (helm-aif (and (markerp cand) (marker-buffer cand)) - (switch-to-buffer it)))) - -(defun helm-imenu--execute-action-at-once-p () - (let ((cur (helm-get-selection)) - (mb (with-helm-current-buffer - (save-excursion - (goto-char (point-at-bol)) - (point-marker))))) - (if (equal (cdr cur) mb) - (prog1 nil - (helm-set-pattern "") - (helm-force-update)) - t))) - -(defun helm-imenu-action (candidate) - "Default action for `helm-source-imenu'." - (helm-log-run-hook 'helm-goto-line-before-hook) - (helm-imenu--maybe-switch-to-buffer candidate) - (imenu candidate) - ;; If semantic is supported in this buffer - ;; imenu used `semantic-imenu-goto-function' - ;; and position have been highlighted, - ;; no need to highlight again. - (unless (eq imenu-default-goto-function - 'semantic-imenu-goto-function) - (helm-highlight-current-line))) - -(defun helm-imenu-persistent-action (candidate) - "Default persistent action for `helm-source-imenu'." - (helm-imenu--maybe-switch-to-buffer candidate) - (imenu candidate) - (helm-highlight-current-line)) - -(defun helm-imenu-candidates (&optional buffer) - (with-current-buffer (or buffer helm-current-buffer) - (let ((tick (buffer-modified-tick))) - (if (eq helm-cached-imenu-tick tick) - helm-cached-imenu-candidates - (setq imenu--index-alist nil) - (prog1 (setq helm-cached-imenu-candidates - (let ((index (imenu--make-index-alist t))) - (helm-imenu--candidates-1 - (delete (assoc "*Rescan*" index) index)))) - (setq helm-cached-imenu-tick tick)))))) - -(defun helm-imenu-candidates-in-all-buffers (&optional build-sources) - (let* ((lst (buffer-list)) - (progress-reporter (make-progress-reporter - "Imenu indexing buffers..." 1 (length lst)))) - (prog1 - (cl-loop with cur-buf = (if build-sources - (current-buffer) helm-current-buffer) - for b in lst - for count from 1 - when (with-current-buffer b - (and (or (member major-mode helm-imenu-extra-modes) - (derived-mode-p 'prog-mode)) - (helm-same-major-mode-p - cur-buf helm-imenu-all-buffer-assoc))) - if build-sources - collect (helm-make-source - (format "Imenu in %s" (buffer-name b)) - 'helm-imenu-source - :candidates (with-current-buffer b - (helm-imenu-candidates b)) - :fuzzy-match helm-imenu-fuzzy-match) - else - append (with-current-buffer b - (helm-imenu-candidates b)) - do (progress-reporter-update progress-reporter count)) - (progress-reporter-done progress-reporter)))) - -(defun helm-imenu--candidates-1 (alist) - (cl-loop for elm in alist - nconc (cond - ((imenu--subalist-p elm) - (helm-imenu--candidates-1 - (cl-loop for (e . v) in (cdr elm) collect - (cons (propertize - e 'helm-imenu-type (car elm)) - ;; If value is an integer, convert it - ;; to a marker, otherwise it is a cons cell - ;; and it will be converted on next recursions. - ;; (Issue #1060) [1]. - (if (integerp v) (copy-marker v) v))))) - ((listp (cdr elm)) - (and elm (list elm))) - (t - ;; bug in imenu, should not be needed. - (and (cdr elm) - ;; Semantic uses overlays whereas imenu uses - ;; markers (issue #1706). - (setcdr elm (pcase (cdr elm) ; Same as [1]. - ((and ov (pred overlayp)) - (copy-overlay ov)) - ((and mk (or (pred markerp) - (pred integerp))) - (copy-marker mk)))) - (list elm)))))) - -(defun helm-imenu--get-prop (item) - ;; property value of ITEM can have itself - ;; a property value which have itself a property value - ;; ...and so on; Return a list of all these - ;; properties values starting at ITEM. - (let* ((prop (get-text-property 0 'helm-imenu-type item)) - (lst (list prop item))) - (when prop - (while prop - (setq prop (get-text-property 0 'helm-imenu-type prop)) - (and prop (push prop lst))) - lst))) - -(defun helm-imenu-transformer (candidates) - (cl-loop for (k . v) in candidates - ;; (k . v) == (symbol-name . marker) - for bufname = (buffer-name - (pcase v - ((pred overlayp) (overlay-buffer v)) - ((or (pred markerp) (pred integerp)) - (marker-buffer v)))) - for types = (or (helm-imenu--get-prop k) - (list (if (with-current-buffer bufname - (derived-mode-p 'prog-mode)) - "Function" - "Top level") - k)) - for disp1 = (mapconcat - (lambda (x) - (propertize - x 'face - (cl-loop for (p . f) in helm-imenu-type-faces - when (string-match p x) return f - finally return 'default))) - types helm-imenu-delimiter) - for disp = (propertize disp1 'help-echo bufname 'types types) - collect - (cons disp (cons k v)))) - -;;;###autoload -(defun helm-imenu () - "Preconfigured `helm' for `imenu'." - (interactive) - (unless helm-source-imenu - (setq helm-source-imenu - (helm-make-source "Imenu" 'helm-imenu-source - :fuzzy-match helm-imenu-fuzzy-match))) - (let ((imenu-auto-rescan t) - (str (thing-at-point 'symbol)) - (helm-execute-action-at-once-if-one - helm-imenu-execute-action-at-once-if-one)) - (helm :sources 'helm-source-imenu - :default (list (concat "\\_<" (and str (regexp-quote str)) "\\_>") str) - :preselect str - :buffer "*helm imenu*"))) - -;;;###autoload -(defun helm-imenu-in-all-buffers () - "Preconfigured helm for fetching imenu entries in all buffers with similar mode as current. -A mode is similar as current if it is the same, it is derived i.e `derived-mode-p' -or it have an association in `helm-imenu-all-buffer-assoc'." - (interactive) - (unless helm-imenu-in-all-buffers-separate-sources - (unless helm-source-imenu-all - (setq helm-source-imenu-all - (helm-make-source "Imenu in all buffers" 'helm-imenu-source - :init (lambda () - ;; Use a cache to avoid repeatedly sending - ;; progress-reporter message when updating - ;; (Issue #1704). - (setq helm-imenu--in-all-buffers-cache - (helm-imenu-candidates-in-all-buffers))) - :candidates 'helm-imenu--in-all-buffers-cache - :fuzzy-match helm-imenu-fuzzy-match)))) - (let ((imenu-auto-rescan t) - (str (thing-at-point 'symbol)) - (helm-execute-action-at-once-if-one - helm-imenu-execute-action-at-once-if-one) - (helm--maybe-use-default-as-input - (not (null (memq 'helm-source-imenu-all - helm-sources-using-default-as-input)))) - (sources (if helm-imenu-in-all-buffers-separate-sources - (helm-imenu-candidates-in-all-buffers 'build-sources) - '(helm-source-imenu-all)))) - (helm :sources sources - :default (list (concat "\\_<" (and str (regexp-quote str)) "\\_>") str) - :preselect (unless helm--maybe-use-default-as-input str) - :buffer "*helm imenu all*"))) - -(provide 'helm-imenu) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-imenu.el ends here diff --git a/elpa/helm-20191031.725/helm-info.el b/elpa/helm-20191031.725/helm-info.el deleted file mode 100644 index c484ab6c..00000000 --- a/elpa/helm-20191031.725/helm-info.el +++ /dev/null @@ -1,268 +0,0 @@ -;;; helm-info.el --- Browse info index with helm -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'cl-lib) -(require 'helm) -(require 'helm-lib) -(require 'helm-utils) -(require 'info) - -(declare-function Info-index-nodes "info" (&optional file)) -(declare-function Info-goto-node "info" (&optional fork)) -(declare-function Info-find-node "info.el" (filename nodename &optional no-going-back)) -(defvar Info-history) -(defvar Info-directory-list) - -;;; Customize - -(defgroup helm-info nil - "Info-related applications and libraries for Helm." - :group 'helm) - -(defcustom helm-info-default-sources - '(helm-source-info-elisp - helm-source-info-cl - helm-source-info-eieio - helm-source-info-pages) - "Default sources to use for looking up symbols at point in Info -files with `helm-info-at-point'." - :group 'helm-info - :type '(repeat (choice symbol))) - -;;; Build info-index sources with `helm-info-source' class. - -(cl-defun helm-info-init (&optional (file (helm-attr 'info-file))) - ;; Allow reinit candidate buffer when using edebug. - (helm-aif (and debug-on-error - (helm-candidate-buffer)) - (kill-buffer it)) - (unless (helm-candidate-buffer) - (save-selected-window - (info file " *helm info temp buffer*") - (let ((tobuf (helm-candidate-buffer 'global)) - Info-history - start end line) - (cl-dolist (node (Info-index-nodes)) - (Info-goto-node node) - (goto-char (point-min)) - (while (search-forward "\n* " nil t) - (unless (search-forward "Menu:\n" (1+ (point-at-eol)) t) - (setq start (point-at-bol) - ;; Fix issue #1503 by getting the invisible - ;; info displayed on next line in long strings. - ;; e.g "* Foo.\n (line 12)" instead of - ;; "* Foo.(line 12)" - end (or (save-excursion - (goto-char (point-at-bol)) - (re-search-forward "(line +[0-9]+)" nil t)) - (point-at-eol)) - ;; Long string have a new line inserted before the - ;; invisible spec, remove it. - line (replace-regexp-in-string - "\n" "" (buffer-substring start end))) - (with-current-buffer tobuf - (insert line) - (insert "\n"))))) - (bury-buffer))))) - -(defun helm-info-goto (node-line) - (Info-goto-node (car node-line)) - (helm-goto-line (cdr node-line))) - -(defun helm-info-display-to-real (line) - (and (string-match - ;; This regexp is stolen from Info-apropos-matches - "\\* +\\([^\n]*.+[^\n]*\\):[ \t]+\\([^\n]*\\)\\.\\(?:[ \t\n]*(line +\\([0-9]+\\))\\)?" line) - (cons (format "(%s)%s" (helm-attr 'info-file) (match-string 2 line)) - (string-to-number (or (match-string 3 line) "1"))))) - -(defclass helm-info-source (helm-source-in-buffer) - ((info-file :initarg :info-file - :initform nil - :custom 'string) - (init :initform #'helm-info-init) - (display-to-real :initform #'helm-info-display-to-real) - (get-line :initform #'buffer-substring) - (action :initform '(("Goto node" . helm-info-goto))))) - -(defmacro helm-build-info-source (fname &rest args) - `(helm-make-source (concat "Info Index: " ,fname) 'helm-info-source - :info-file ,fname ,@args)) - -(defun helm-build-info-index-command (name doc source buffer) - "Define a helm command NAME with documentation DOC. -Arg SOURCE will be an existing helm source named -`helm-source-info-' and BUFFER a string buffer name." - (defalias (intern (concat "helm-info-" name)) - (lambda () - (interactive) - (helm :sources source - :buffer buffer - :candidate-number-limit 1000)) - doc)) - -(defun helm-define-info-index-sources (var-value &optional commands) - "Define helm sources named helm-source-info-. -Sources are generated for all entries of `helm-default-info-index-list'. -If COMMANDS arg is non-nil, also build commands named `helm-info-'. -Where NAME is an element of `helm-default-info-index-list'." - (cl-loop for str in var-value - for sym = (intern (concat "helm-source-info-" str)) - do (set sym (helm-build-info-source str)) - when commands - do (helm-build-info-index-command - str (format "Predefined helm for %s info." str) - sym (format "*helm info %s*" str)))) - -(defun helm-info-index-set (var value) - (set var value) - (helm-define-info-index-sources value t)) - -;;; Search Info files - -;; `helm-info' is the main entry point here. It prompts the user for an Info -;; file, then a term in the file's index to jump to. - -(defvar helm-info-searched (make-ring 32) - "Ring of previously searched Info files.") - -(defun helm-get-info-files () - "Return list of Info files to use for `helm-info'. - -Elements of the list are strings of Info file names without -extensions (e.g. \"emacs\" for file \"emacs.info.gz\"). Info -files are found by searching directories in -`Info-directory-list'." - (info-initialize) ; Build Info-directory-list from INFOPATH (Issue #2118) - (let ((files (cl-loop for d in (or Info-directory-list - Info-default-directory-list) - when (file-directory-p d) - append (directory-files d nil "\\.info")))) - (helm-fast-remove-dups - (cl-loop for f in files collect - (helm-file-name-sans-extension f)) - :test 'equal))) - -(defcustom helm-default-info-index-list - (helm-get-info-files) - "Info files to search in with `helm-info'." - :group 'helm-info - :type '(repeat (choice string)) - :set 'helm-info-index-set) - -(defun helm-info-search-index (candidate) - "Search the index of CANDIDATE's Info file using the function -helm-info-." - (let ((helm-info-function - (intern-soft (concat "helm-info-" candidate)))) - (when (fboundp helm-info-function) - (funcall helm-info-function) - (ring-insert helm-info-searched candidate)))) - -(defun helm-def-source--info-files () - "Return a `helm' source for Info files." - (helm-build-sync-source "Helm Info" - :candidates - (lambda () (copy-sequence helm-default-info-index-list)) - :candidate-number-limit 999 - :candidate-transformer - (lambda (candidates) - (sort candidates #'string-lessp)) - :nomark t - :action '(("Search index" . helm-info-search-index)))) - -;;;###autoload -(defun helm-info (&optional refresh) - "Preconfigured `helm' for searching Info files' indices. - -With a prefix argument \\[universal-argument], set REFRESH to non-nil. - -Optional parameter REFRESH, when non-nil, reevaluates -`helm-default-info-index-list'. If the variable has been -customized, set it to its saved value. If not, set it to its -standard value. See `custom-reevaluate-setting' for more. - -REFRESH is useful when new Info files are installed. If -`helm-default-info-index-list' has not been customized, the new -Info files are made available." - (interactive "P") - (let ((default (unless (ring-empty-p helm-info-searched) - (ring-ref helm-info-searched 0)))) - (when refresh - (custom-reevaluate-setting 'helm-default-info-index-list)) - (helm :sources (helm-def-source--info-files) - :buffer "*helm Info*" - :preselect (and default - (concat "\\_<" (regexp-quote default) "\\_>"))))) - -;;;; Info at point - -;; `helm-info-at-point' is the main entry point here. It searches for the -;; symbol at point through the Info sources defined in -;; `helm-info-default-sources' and jumps to it. - -(defvar helm-info--pages-cache nil - "Cache for all Info pages on the system.") - -(defvar helm-source-info-pages - (helm-build-sync-source "Info Pages" - :init #'helm-info-pages-init - :candidates (lambda () helm-info--pages-cache) - :action '(("Show with Info" . - (lambda (node-str) - (info (replace-regexp-in-string - "^[^:]+: " "" node-str))))) - :requires-pattern 2) - "Helm source for Info pages.") - -(defun helm-info-pages-init () - "Collect candidates for initial Info node Top." - (or helm-info--pages-cache - (let ((info-topic-regexp "\\* +\\([^:]+: ([^)]+)[^.]*\\)\\.")) - (save-selected-window - (info "dir" " *helm info temp buffer*") - (Info-find-node "dir" "top") - (goto-char (point-min)) - (while (re-search-forward info-topic-regexp nil t) - (push (match-string-no-properties 1) - helm-info--pages-cache)) - (kill-buffer))))) - -;;;###autoload -(defun helm-info-at-point () - "Preconfigured `helm' for searching info at point." - (interactive) - (cl-loop for src in helm-info-default-sources - for name = (if (symbolp src) - (assoc 'name (symbol-value src)) - (assoc 'name src)) - unless name - do (warn "Couldn't build source `%S' without its info file" src)) - (helm :sources helm-info-default-sources - :buffer "*helm info*")) - -(provide 'helm-info) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-info.el ends here diff --git a/elpa/helm-20191031.725/helm-locate.el b/elpa/helm-20191031.725/helm-locate.el deleted file mode 100644 index ecba5cd5..00000000 --- a/elpa/helm-20191031.725/helm-locate.el +++ /dev/null @@ -1,469 +0,0 @@ -;;; helm-locate.el --- helm interface for locate. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;; NOTE for WINDOZE users: -;; You have to install Everything with his command line interface here: -;; http://www.voidtools.com/download.php - -;;; Code: - -(require 'cl-lib) -(require 'helm) -(require 'helm-types) -(require 'helm-help) - - -(defgroup helm-locate nil - "Locate related Applications and libraries for Helm." - :group 'helm) - -(defcustom helm-locate-db-file-regexp "m?locate\.db$" - "Default regexp to match locate database. -If nil Search in all files." - :type 'string - :group 'helm-locate) - -(defcustom helm-ff-locate-db-filename "locate.db" - "The basename of the locatedb file you use locally in your directories. -When this is set and `helm' find such a file in the directory from -where you launch locate, it will use this file and will not prompt you -for a db file. -Note that this happen only when locate is launched with a prefix arg." - :group 'helm-locate - :type 'string) - -(defcustom helm-locate-command nil - "A list of arguments for locate program. - -Helm will calculate a default value for your system on startup unless -`helm-locate-command' is non-nil, here the default values it will use -according to your system: - -Gnu/linux: \"locate %s -e -A --regex %s\" -berkeley-unix: \"locate %s %s\" -windows-nt: \"es %s %s\" -Others: \"locate %s %s\" - -This string will be passed to format so it should end with `%s'. -The first format spec is used for the \"-i\" value of locate/es, -So don't set it directly but use `helm-locate-case-fold-search' -for this. - -The last option must be the one preceding pattern i.e \"-r\" or \"--regex\". - -You will be able to pass other options such as \"-b\" or \"l\" -during helm invocation after entering pattern only when multi matching, -not when fuzzy matching. - -Note that the \"-b\" option is added automatically by helm when -var `helm-locate-fuzzy-match' is non-nil and switching back from -multimatch to fuzzy matching (this is done automatically when a space -is detected in pattern)." - :type 'string - :group 'helm-locate) - -(defcustom helm-locate-create-db-command - "updatedb -l 0 -o '%s' -U '%s'" - "Command used to create a locale locate db file." - :type 'string - :group 'helm-locate) - -(defcustom helm-locate-case-fold-search helm-case-fold-search - "It have the same meaning as `helm-case-fold-search'. -The -i option of locate will be used depending of value of -`helm-pattern' when this is set to 'smart. -When nil \"-i\" will not be used at all. -and when non--nil it will always be used. -NOTE: the -i option of the \"es\" command used on windows does -the opposite of \"locate\" command." - :group 'helm-locate - :type 'symbol) - -(defcustom helm-locate-fuzzy-match nil - "Enable fuzzy matching in `helm-locate'. -Note that when this is enabled searching is done on basename." - :group 'helm-locate - :type 'boolean) - -(defcustom helm-locate-fuzzy-sort-fn - #'helm-locate-default-fuzzy-sort-fn - "Default fuzzy matching sort function for locate." - :group 'helm-locate - :type 'boolean) - -(defcustom helm-locate-project-list nil - "A list of directories, your projects. -When set, allow browsing recursively files in all -directories of this list with `helm-projects-find-files'." - :group 'helm-locate - :type '(repeat string)) - -(defcustom helm-locate-recursive-dirs-command "locate -i -e -A --regex '^%s' '%s.*$'" - "Command used for recursive directories completion in `helm-find-files'. - -For Windows and `es' use something like \"es -r ^%s.*%s.*$\" - -The two format specs are mandatory. - -If for some reasons you can't use locate because your filesystem -doesn't have a data base, you can use find command from findutils but -be aware that it will be much slower, see `helm-find-files' embebded -help for more infos." - :type 'string - :group 'helm-files) - - -(defvar helm-locate-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-generic-files-map) - (define-key map (kbd "DEL") 'helm-delete-backward-no-update) - map)) - -(defface helm-locate-finish - '((t (:foreground "Green"))) - "Face used in mode line when locate process is finish." - :group 'helm-locate) - - -(defun helm-ff-find-locatedb (&optional from-ff) - "Try to find if a local locatedb file is available. -The search is done in `helm-ff-default-directory' or -fall back to `default-directory' if FROM-FF is nil." - (helm-aif (and helm-ff-locate-db-filename - (locate-dominating-file - (or (and from-ff - helm-ff-default-directory) - default-directory) - helm-ff-locate-db-filename)) - (expand-file-name helm-ff-locate-db-filename it))) - -(defun helm-locate-create-db-default-function (db-name directory) - "Default function used to create a locale locate db file. -Argument DB-NAME name of the db file. -Argument DIRECTORY root of file system subtree to scan." - (format helm-locate-create-db-command - db-name (expand-file-name directory))) - -(defvar helm-locate-create-db-function - #'helm-locate-create-db-default-function - "Function used to create a locale locate db file. -It should receive the same arguments as -`helm-locate-create-db-default-function'.") - -(defun helm-locate-1 (&optional localdb init from-ff default) - "Generic function to run Locate. -Prefix arg LOCALDB when (4) search and use a local locate db file when it -exists or create it, when (16) force update of existing db file -even if exists. -It have no effect when locate command is 'es'. -INIT is a string to use as initial input in prompt. -See `helm-locate-with-db' and `helm-locate'." - (require 'helm-mode) - (helm-locate-set-command) - (let ((pfn (lambda (candidate) - (if (file-directory-p candidate) - (message "Error: The locate Db should be a file") - (if (= (shell-command - (funcall helm-locate-create-db-function - candidate - helm-ff-default-directory)) - 0) - (message "New locatedb file `%s' created" candidate) - (error "Failed to create locatedb file `%s'" candidate))))) - (locdb (and localdb - (not (string-match "^es" helm-locate-command)) - (or (and (equal '(4) localdb) - (helm-ff-find-locatedb from-ff)) - (helm-read-file-name - "Create Locate Db file: " - :initial-input (expand-file-name "locate.db" - (or helm-ff-default-directory - default-directory)) - :preselect helm-locate-db-file-regexp - :test (lambda (x) - (if helm-locate-db-file-regexp - ;; Select only locate db files and directories - ;; to allow navigation. - (or (string-match - helm-locate-db-file-regexp x) - (file-directory-p x)) - x))))))) - (when (and locdb (or (equal localdb '(16)) - (not (file-exists-p locdb)))) - (funcall pfn locdb)) - (helm-locate-with-db (and localdb locdb) init default))) - -(defun helm-locate-set-command () - "Setup `helm-locate-command' if not already defined." - (unless helm-locate-command - (setq helm-locate-command - (cl-case system-type - (gnu/linux "locate %s -e -A --regex %s") - (berkeley-unix "locate %s %s") - (windows-nt "es %s %s") - (t "locate %s %s"))))) - -(defun helm-locate-initial-setup () - (require 'helm-for-files) - (helm-locate-set-command)) - -(defvar helm-file-name-history nil) -(defun helm-locate-with-db (&optional db initial-input default) - "Run locate -d DB. -If DB is not given or nil use locate without -d option. -Argument DB can be given as a string or list of db files. -Argument INITIAL-INPUT is a string to use as initial-input. -See also `helm-locate'." - (require 'helm-files) - (when (and db (stringp db)) (setq db (list db))) - (helm-locate-set-command) - (let ((helm-locate-command - (if db - (replace-regexp-in-string - "locate" - (format (if helm-locate-fuzzy-match - "locate -b -d '%s'" "locate -d '%s'") - (mapconcat 'identity - ;; Remove eventually - ;; marked directories by error. - (cl-loop for i in db - unless (file-directory-p i) - ;; expand-file-name to resolve - ;; abbreviated fnames not - ;; expanding inside single - ;; quotes i.e. '%s'. - collect (expand-file-name i)) - ":")) - helm-locate-command) - (if (and helm-locate-fuzzy-match - (not (string-match-p "\\`locate -b" helm-locate-command))) - (replace-regexp-in-string - "\\`locate" "locate -b" helm-locate-command) - helm-locate-command)))) - (setq helm-file-name-history (mapcar 'helm-basename file-name-history)) - (helm :sources 'helm-source-locate - :buffer "*helm locate*" - :ff-transformer-show-only-basename nil - :input initial-input - :default default - :history 'helm-file-name-history))) - -(defun helm-locate-update-mode-line (process-name) - "Update mode-line with PROCESS-NAME status information." - (with-helm-window - (setq mode-line-format - `(" " mode-line-buffer-identification " " - (:eval (format "L%s" (helm-candidate-number-at-point))) " " - (:eval (propertize - (format "[%s process finished - (%s results)]" - (max (1- (count-lines - (point-min) (point-max))) - 0) - ,process-name) - 'face 'helm-locate-finish)))) - (force-mode-line-update))) - -(defun helm-locate-init () - "Initialize async locate process for `helm-source-locate'." - (let* ((locate-is-es (string-match "\\`es" helm-locate-command)) - (real-locate (string-match "\\`locate" helm-locate-command)) - (case-sensitive-flag (if locate-is-es "-i" "")) - (ignore-case-flag (if (or locate-is-es - (not real-locate)) "" "-i")) - (args (helm-mm-split-pattern helm-pattern)) - (cmd (format helm-locate-command - (cl-case helm-locate-case-fold-search - (smart (let ((case-fold-search nil)) - (if (string-match "[[:upper:]]" helm-pattern) - case-sensitive-flag - ignore-case-flag))) - (t (if helm-locate-case-fold-search - ignore-case-flag - case-sensitive-flag))) - (concat - ;; The pattern itself. - (shell-quote-argument (car args)) " " - ;; Possible locate args added - ;; after pattern, don't quote them. - (mapconcat 'identity (cdr args) " ")))) - (default-directory (if (file-directory-p default-directory) - default-directory "/"))) - (helm-log "Starting helm-locate process") - (helm-log "Command line used was:\n\n%s" - (concat ">>> " (propertize cmd 'face 'font-lock-comment-face) "\n\n")) - (prog1 - (start-process-shell-command - "locate-process" helm-buffer - cmd) - (set-process-sentinel - (get-buffer-process helm-buffer) - (lambda (process event) - (let* ((err (process-exit-status process)) - (noresult (= err 1))) - (cond (noresult - (with-helm-buffer - (unless (cdr helm-sources) - (insert (concat "* Exit with code 1, no result found," - " command line was:\n\n " - cmd))))) - ((string= event "finished\n") - (when (and helm-locate-fuzzy-match - (not (string-match-p "\\s-" helm-pattern))) - (helm-redisplay-buffer)) - (helm-locate-update-mode-line "Locate")) - (t - (helm-log "Error: Locate %s" - (replace-regexp-in-string "\n" "" event)))))))))) - -(defun helm-locate-default-fuzzy-sort-fn (candidates) - "Default sort function for files in fuzzy matching. -Sort is done on basename of CANDIDATES." - (helm-fuzzy-matching-default-sort-fn-1 candidates nil t)) - -(defclass helm-locate-override-inheritor (helm-type-file) ()) - -(defclass helm-locate-source (helm-source-async helm-locate-override-inheritor) - ((init :initform 'helm-locate-initial-setup) - (candidates-process :initform 'helm-locate-init) - (requires-pattern :initform 3) - (history :initform 'helm-file-name-history) - (persistent-action :initform 'helm-ff-kill-or-find-buffer-fname) - (candidate-number-limit :initform 9999) - (redisplay :initform (progn helm-locate-fuzzy-sort-fn)) - (group :initform 'helm-locate))) - -;; Override helm-type-file class keymap. -(defmethod helm--setup-source :after ((source helm-locate-override-inheritor)) - (setf (slot-value source 'keymap) helm-locate-map)) - -(defvar helm-source-locate - (helm-make-source "Locate" 'helm-locate-source - :pattern-transformer 'helm-locate-pattern-transformer - ;; :match-part is only used here to tell helm which part - ;; of candidate to highlight. - :match-part (lambda (candidate) - (if (or (string-match-p " -b\\'" helm-pattern) - (and helm-locate-fuzzy-match - (not (string-match "\\s-" helm-pattern)))) - (helm-basename candidate) - candidate)))) - -(defun helm-locate-pattern-transformer (pattern) - (if helm-locate-fuzzy-match - ;; When fuzzy is enabled helm add "-b" option on startup. - (cond ((string-match-p " " pattern) - (when (string-match "\\`locate -b" helm-locate-command) - (setq helm-locate-command - (replace-match "locate" t t helm-locate-command))) - pattern) - (t - (unless (string-match-p "\\`locate -b" helm-locate-command) - (setq helm-locate-command - (replace-regexp-in-string - "\\`locate" "locate -b" helm-locate-command))) - (helm--mapconcat-pattern pattern))) - pattern)) - -(defun helm-locate-find-dbs-in-projects (&optional update) - (let* ((pfn (lambda (candidate directory) - (unless (= (shell-command - (funcall helm-locate-create-db-function - candidate - directory)) - 0) - (error "Failed to create locatedb file `%s'" candidate))))) - (cl-loop for p in helm-locate-project-list - for db = (expand-file-name - helm-ff-locate-db-filename - (file-name-as-directory p)) - if (and (null update) (file-exists-p db)) - collect db - else do (funcall pfn db p) - and collect db))) - -;;; Directory completion for hff. -;; -(defclass helm-locate-subdirs-source (helm-source-in-buffer) - ((basedir :initarg :basedir - :initform nil - :custom string) - (subdir :initarg :subdir - :initform nil - :custom 'string) - (data :initform #'helm-locate-init-subdirs) - (group :initform 'helm-locate))) - -(defun helm-locate-init-subdirs () - (with-temp-buffer - (call-process-shell-command - (format helm-locate-recursive-dirs-command - (if (string-match-p "\\`es" helm-locate-recursive-dirs-command) - ;; Fix W32 paths. - (replace-regexp-in-string - "/" "\\\\\\\\" (helm-attr 'basedir)) - (helm-attr 'basedir)) - (helm-attr 'subdir)) - nil t nil) - (buffer-string))) - -;;;###autoload -(defun helm-projects-find-files (update) - "Find files with locate in `helm-locate-project-list'. -With a prefix arg refresh the database in each project." - (interactive "P") - (helm-locate-set-command) - (cl-assert (and (string-match-p "\\`locate" helm-locate-command) - (executable-find "updatedb")) - nil "Unsupported locate version") - (let ((dbs (helm-locate-find-dbs-in-projects update))) - (if dbs - (helm-locate-with-db dbs) - (user-error "No projects found, please setup `helm-locate-project-list'")))) - -;;;###autoload -(defun helm-locate (arg) - "Preconfigured `helm' for Locate. -Note: you can add locate options after entering pattern. -See 'man locate' for valid options and also `helm-locate-command'. - -You can specify a local database with prefix argument ARG. -With two prefix arg, refresh the current local db or create it -if it doesn't exists. - -To create a user specific db, use -\"updatedb -l 0 -o db_path -U directory\". -Where db_path is a filename matched by -`helm-locate-db-file-regexp'." - (interactive "P") - (helm-set-local-variable 'helm-async-outer-limit-hook - (list (lambda () - (when (and helm-locate-fuzzy-match - (not (string-match-p - "\\s-" helm-pattern))) - (helm-redisplay-buffer))))) - (setq helm-ff-default-directory default-directory) - (helm-locate-1 arg nil nil (thing-at-point 'filename))) - -(provide 'helm-locate) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-locate.el ends here diff --git a/elpa/helm-20191031.725/helm-man.el b/elpa/helm-20191031.725/helm-man.el deleted file mode 100644 index 26f8135f..00000000 --- a/elpa/helm-20191031.725/helm-man.el +++ /dev/null @@ -1,119 +0,0 @@ -;;; helm-man.el --- Man and woman UI -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'cl-lib) -(require 'helm) -(require 'helm-help) - -(defvar woman-topic-all-completions) -(defvar woman-manpath) -(defvar woman-path) -(defvar woman-expanded-directory-path) -(declare-function woman-file-name "woman.el" (topic &optional re-cache)) -(declare-function woman-file-name-all-completions "woman.el" (topic)) -(declare-function Man-getpage-in-background "man.el" (topic)) -(declare-function woman-expand-directory-path "woman.el" (path-dirs path-regexps)) -(declare-function woman-topic-all-completions "woman.el" (path)) -(declare-function helm-generic-sort-fn "helm-utils.el" (S1 S2)) - -(defgroup helm-man nil - "Man and Woman applications for helm." - :group 'helm) - -(defcustom helm-man-or-woman-function 'Man-getpage-in-background - "Default command to display a man page." - :group 'helm-man - :type '(radio :tag "Preferred command to display a man page" - (const :tag "Man" Man-getpage-in-background) - (const :tag "Woman" woman))) - -(defcustom helm-man-format-switches (cl-case system-type - ((darwin macos) "%s") - (t "-l %s")) - "Arguments to pass to the `manual-entry' function. -Arguments are passed to `manual-entry' with `format.'" - :group 'helm-man - :type 'string) - -;; Internal -(defvar helm-man--pages nil - "All man pages on system. -Will be calculated the first time you invoke helm with this -source.") - -(defun helm-man-default-action (candidate) - "Default action for jumping to a woman or man page from helm." - (let ((wfiles (mapcar #'car (woman-file-name-all-completions candidate)))) - (condition-case nil - (let ((file (if (cdr wfiles) - (helm-comp-read "ManFile: " wfiles :must-match t) - (car wfiles)))) - (if (eq helm-man-or-woman-function 'Man-getpage-in-background) - (manual-entry (format helm-man-format-switches file)) - (condition-case nil - (woman-find-file file) - ;; If woman is unable to format correctly - ;; try Man instead. - (error (kill-buffer) - (manual-entry (format helm-man-format-switches file)))))) - ;; If even Man failed with file as argument, try again with Man - ;; but using Topic candidate instead of the file calculated by - ;; woman. - (error (kill-buffer) - (Man-getpage-in-background candidate))))) - -(defun helm-man--init () - (require 'woman) - (require 'helm-utils) - (unless helm-man--pages - (setq woman-expanded-directory-path - (woman-expand-directory-path woman-manpath woman-path)) - (setq woman-topic-all-completions - (woman-topic-all-completions woman-expanded-directory-path)) - (setq helm-man--pages (mapcar 'car woman-topic-all-completions))) - (helm-init-candidates-in-buffer 'global helm-man--pages)) - -(defvar helm-source-man-pages - (helm-build-in-buffer-source "Manual Pages" - :init #'helm-man--init - :persistent-action #'ignore - :filtered-candidate-transformer - (lambda (candidates _source) - (sort candidates #'helm-generic-sort-fn)) - :action '(("Display Man page" . helm-man-default-action)) - :group 'helm-man)) - -;;;###autoload -(defun helm-man-woman (arg) - "Preconfigured `helm' for Man and Woman pages. -With a prefix arg reinitialize the cache." - (interactive "P") - (when arg (setq helm-man--pages nil)) - (helm :sources 'helm-source-man-pages - :buffer "*helm man woman*")) - -(provide 'helm-man) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-man.el ends here diff --git a/elpa/helm-20191031.725/helm-misc.el b/elpa/helm-20191031.725/helm-misc.el deleted file mode 100644 index 7843f0fb..00000000 --- a/elpa/helm-20191031.725/helm-misc.el +++ /dev/null @@ -1,333 +0,0 @@ -;;; helm-misc.el --- Various functions for helm -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: -(require 'cl-lib) -(require 'helm) -(require 'helm-help) -(require 'helm-types) - -(declare-function display-time-world-display "time.el") -(defvar display-time-world-list) -(declare-function LaTeX-math-mode "ext:latex.el") -(declare-function jabber-chat-with "ext:jabber.el") -(declare-function jabber-read-account "ext:jabber.el") - - -(defgroup helm-misc nil - "Various Applications and libraries for Helm." - :group 'helm) - -(defcustom helm-time-zone-home-location "Paris" - "The time zone of your home" - :group 'helm-misc - :type 'string) - -(defcustom helm-timezone-actions - '(("Set timezone env (TZ)" . (lambda (candidate) - (setenv "TZ" candidate)))) - "Actions for helm-timezone." - :group 'helm-misc - :type '(alist :key-type string :value-type function)) - -(defface helm-time-zone-current - '((t (:foreground "green"))) - "Face used to colorize current time in `helm-world-time'." - :group 'helm-misc) - -(defface helm-time-zone-home - '((t (:foreground "red"))) - "Face used to colorize home time in `helm-world-time'." - :group 'helm-misc) - - - -;;; Latex completion -;; -;; Test -;; (setq LaTeX-math-menu '("Math" -;; ["foo" val0 t] -;; ("bar" -;; ["baz" val1 t]) -;; ("aze" -;; ["zer" val2 t]) -;; ("AMS" -;; ("rec" -;; ["fer" val3 t]) -;; ("rty" -;; ["der" val4 t])) -;; ("ABC" -;; ("xcv" -;; ["sdf" val5 t]) -;; ("dfg" -;; ["fgh" val6 t])))) -;; (helm-latex-math-candidates) -;; => -;; (("foo" . val0) -;; ("baz" . val1) -;; ("zer" . val2) -;; ("fer" . val3) -;; ("der" . val4) -;; ("sdf" . val5) -;; ("fgh" . val6)) - -(defvar LaTeX-math-menu) -(defun helm-latex-math-candidates () - (cl-labels ((helm-latex--math-collect (L) - (cond ((vectorp L) - (list (cons (aref L 0) (aref L 1)))) - ((listp L) - (cl-loop for a in L nconc - (helm-latex--math-collect a)))))) - (helm-latex--math-collect LaTeX-math-menu))) - -(defvar helm-source-latex-math - (helm-build-sync-source "Latex Math Menu" - :init (lambda () - (with-helm-current-buffer - (LaTeX-math-mode 1))) - :candidate-number-limit 9999 - :candidates 'helm-latex-math-candidates - :action (lambda (candidate) - (call-interactively candidate)))) - - -;;; Jabber Contacts (jabber.el) -(defun helm-jabber-online-contacts () - "List online Jabber contacts." - (with-no-warnings - (cl-loop for item in (jabber-concat-rosters) - when (get item 'connected) - collect - (if (get item 'name) - (cons (get item 'name) item) - (cons (symbol-name item) item))))) - -(defvar helm-source-jabber-contacts - (helm-build-sync-source "Jabber Contacts" - :init (lambda () (require 'jabber)) - :candidates (lambda () (mapcar 'car (helm-jabber-online-contacts))) - :action (lambda (x) - (jabber-chat-with - (jabber-read-account) - (symbol-name - (cdr (assoc x (helm-jabber-online-contacts)))))))) - -;;; World time -;; -(defvar zoneinfo-style-world-list) -(defvar legacy-style-world-list) - -(defun helm-time-zone-transformer (candidates _source) - (cl-loop for i in candidates - for (z . p) in display-time-world-list - collect - (cons - (cond ((string-match (format-time-string "%H:%M" (current-time)) i) - (propertize i 'face 'helm-time-zone-current)) - ((string-match helm-time-zone-home-location i) - (propertize i 'face 'helm-time-zone-home)) - (t i)) - z))) - -(defvar helm-source-time-world - (helm-build-in-buffer-source "Time World List" - :init (lambda () - (require 'time) - (unless (and display-time-world-list - (listp display-time-world-list)) - ;; adapted from `time--display-world-list' from - ;; emacs-27 for compatibility as - ;; `display-time-world-list' is set by default to t. - (setq display-time-world-list - ;; Determine if zoneinfo style timezones are - ;; supported by testing that America/New York and - ;; Europe/London return different timezones. - (let ((nyt (format-time-string "%z" nil "America/New_York")) - (gmt (format-time-string "%z" nil "Europe/London"))) - (if (string-equal nyt gmt) - legacy-style-world-list - zoneinfo-style-world-list))))) - :data (lambda () - (with-temp-buffer - (display-time-world-display display-time-world-list) - (buffer-string))) - :action 'helm-timezone-actions - :filtered-candidate-transformer 'helm-time-zone-transformer)) - -;;; Commands -;; -(defun helm-call-interactively (cmd-or-name) - "Execute CMD-OR-NAME as Emacs command. -It is added to `extended-command-history'. -`helm-current-prefix-arg' is used as the command's prefix argument." - (setq extended-command-history - (cons (helm-stringify cmd-or-name) - (delete (helm-stringify cmd-or-name) extended-command-history))) - (let ((current-prefix-arg helm-current-prefix-arg) - (cmd (helm-symbolify cmd-or-name))) - (if (stringp (symbol-function cmd)) - (execute-kbd-macro (symbol-function cmd)) - (setq this-command cmd) - (call-interactively cmd)))) - -;;; Minibuffer History -;; -;; -(defvar helm-minibuffer-history-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map [remap helm-minibuffer-history] 'undefined) - map)) - -(defcustom helm-minibuffer-history-must-match t - "Allow inserting non matching elements when nil or 'confirm." - :group 'helm-misc - :type '(choice - (const :tag "Must match" t) - (const :tag "Confirm" 'confirm) - (const :tag "Always allow" nil))) - - -;;; Helm ratpoison UI -;; -;; -(defvar helm-source-ratpoison-commands - (helm-build-in-buffer-source "Ratpoison Commands" - :init 'helm-ratpoison-commands-init - :action (helm-make-actions - "Execute the command" 'helm-ratpoison-commands-execute) - :display-to-real 'helm-ratpoison-commands-display-to-real - :candidate-number-limit 999999)) - -(defun helm-ratpoison-commands-init () - (unless (helm-candidate-buffer) - (with-current-buffer (helm-candidate-buffer 'global) - ;; with ratpoison prefix key - (save-excursion - (call-process "ratpoison" nil (current-buffer) nil "-c" "help")) - (while (re-search-forward "^\\([^ ]+\\) \\(.+\\)$" nil t) - (replace-match " \\1: \\2")) - (goto-char (point-max)) - ;; direct binding - (save-excursion - (call-process "ratpoison" nil (current-buffer) nil "-c" "help top")) - (while (re-search-forward "^\\([^ ]+\\) \\(.+\\)$" nil t) - (replace-match "\\1: \\2"))))) - -(defun helm-ratpoison-commands-display-to-real (display) - (and (string-match ": " display) - (substring display (match-end 0)))) - -(defun helm-ratpoison-commands-execute (candidate) - (call-process "ratpoison" nil nil nil "-ic" candidate)) - -;;; Helm stumpwm UI -;; -;; -(defvar helm-source-stumpwm-commands - (helm-build-in-buffer-source "Stumpwm Commands" - :init 'helm-stumpwm-commands-init - :action (helm-make-actions - "Execute the command" 'helm-stumpwm-commands-execute) - :candidate-number-limit 999999)) - -(defun helm-stumpwm-commands-init () - (with-current-buffer (helm-candidate-buffer 'global) - (save-excursion - (call-process "stumpish" nil (current-buffer) nil "commands")) - (while (re-search-forward "[ ]*\\([^ ]+\\)[ ]*\n?" nil t) - (replace-match "\n\\1\n")) - (delete-blank-lines) - (sort-lines nil (point-min) (point-max)) - (goto-char (point-max)))) - -(defun helm-stumpwm-commands-execute (candidate) - (call-process "stumpish" nil nil nil candidate)) - -;;;###autoload -(defun helm-world-time () - "Preconfigured `helm' to show world time. -Default action change TZ environment variable locally to emacs." - (interactive) - (helm-other-buffer 'helm-source-time-world "*helm world time*")) - -;;;###autoload -(defun helm-insert-latex-math () - "Preconfigured helm for latex math symbols completion." - (interactive) - (helm-other-buffer 'helm-source-latex-math "*helm latex*")) - -;;;###autoload -(defun helm-ratpoison-commands () - "Preconfigured `helm' to execute ratpoison commands." - (interactive) - (helm-other-buffer 'helm-source-ratpoison-commands - "*helm ratpoison commands*")) - -;;;###autoload -(defun helm-stumpwm-commands() - "Preconfigured helm for stumpwm commands." - (interactive) - (helm-other-buffer 'helm-source-stumpwm-commands - "*helm stumpwm commands*")) - -;;;###autoload -(defun helm-minibuffer-history () - "Preconfigured `helm' for `minibuffer-history'." - (interactive) - (cl-assert (minibuffer-window-active-p (selected-window)) nil - "Error: Attempt to use minibuffer history outside a minibuffer") - (let* ((enable-recursive-minibuffers t) - (query-replace-p (or (eq last-command 'query-replace) - (eq last-command 'query-replace-regexp))) - (elm (helm-comp-read "pattern: " - (cl-loop for i in - (symbol-value minibuffer-history-variable) - unless (string= "" i) collect i into history - finally return - (if (consp (car history)) - (mapcar 'prin1-to-string history) - history)) - :header-name - (lambda (name) - (format "%s (%s)" name minibuffer-history-variable)) - :buffer "*helm minibuffer-history*" - :must-match helm-minibuffer-history-must-match - :multiline t - :keymap helm-minibuffer-history-map - :allow-nest t))) - ;; Fix issue #1667 with emacs-25+ `query-replace-from-to-separator'. - (when (and (boundp 'query-replace-from-to-separator) query-replace-p) - (let ((pos (string-match "\0" elm))) - (and pos - (add-text-properties - pos (1+ pos) - `(display ,query-replace-from-to-separator separator t) - elm)))) - (delete-minibuffer-contents) - (insert elm))) - -(provide 'helm-misc) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-misc.el ends here diff --git a/elpa/helm-20191031.725/helm-mode.el b/elpa/helm-20191031.725/helm-mode.el deleted file mode 100644 index 36521a4b..00000000 --- a/elpa/helm-20191031.725/helm-mode.el +++ /dev/null @@ -1,1727 +0,0 @@ -;;; helm-mode.el --- Enable helm completion everywhere. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'cl-lib) -(require 'helm) -(require 'helm-lib) -(require 'helm-files) - -(defvar crm-separator) -(defvar ido-everywhere) -(declare-function ido-mode "ido.el") - -(defgroup helm-mode nil - "Enable helm completion." - :group 'helm) - -(defcustom helm-completing-read-handlers-alist - '((describe-function . helm-completing-read-symbols) - (describe-variable . helm-completing-read-symbols) - (describe-symbol . helm-completing-read-symbols) - (debug-on-entry . helm-completing-read-symbols) - (find-function . helm-completing-read-symbols) - (disassemble . helm-completing-read-symbols) - (trace-function . helm-completing-read-symbols) - (trace-function-foreground . helm-completing-read-symbols) - (trace-function-background . helm-completing-read-symbols) - (find-tag . helm-completing-read-default-find-tag) - (xref-find-definitions . helm-completing-read-default-find-tag) - (xref-find-references . helm-completing-read-default-find-tag) - (ffap-alternate-file . nil) - (tmm-menubar . nil) - (find-file . nil) - (find-file-at-point . helm-completing-read-sync-default-handler) - (ffap . helm-completing-read-sync-default-handler) - (execute-extended-command . nil) - (dired-do-rename . helm-read-file-name-handler-1) - (dired-do-copy . helm-read-file-name-handler-1) - (dired-do-symlink . helm-read-file-name-handler-1) - (dired-do-relsymlink . helm-read-file-name-handler-1) - (dired-do-hardlink . helm-read-file-name-handler-1) - (basic-save-buffer . helm-read-file-name-handler-1) - (write-file . helm-read-file-name-handler-1) - (write-region . helm-read-file-name-handler-1)) - "Completing read functions for specific Emacs commands. - -By default `helm-mode' use `helm-completing-read-default-handler' to -provide helm completion in each `completing-read' or `read-file-name' -found, but other functions can be specified here for specific -commands. This also allow disabling helm completion for some commands -when needed. - -Each entry is a cons cell like (EMACS_COMMAND . COMPLETING-READ_HANDLER) -where key and value are symbols. - -Each key is an Emacs command that use originaly `completing-read'. - -Each value maybe a helm function that takes same arguments as -`completing-read' plus NAME and BUFFER, where NAME is the name of the new -helm source and BUFFER the name of the buffer we will use, but it can -be also a function not using helm, in this case the function should -take same args as `completing-read' and not be prefixed by \"helm-\". - -`helm' will use the name of the command calling `completing-read' as -NAME and BUFFER will be computed as well with NAME but prefixed with -\"*helm-mode-\". - -This function prefix name must start by \"helm-\" when it uses helm, -otherwise `helm' assumes the function is not a helm function and -expects same args as `completing-read', this allow you to define a -handler not using helm completion. - -Example: - - (defun foo/test () - (interactive) - (message \"%S\" (completing-read \"test: \" '(a b c d e)))) - - (defun helm-foo/test-completing-read-handler (prompt collection - predicate require-match - initial-input hist def - inherit-input-method - name buffer) - (helm-comp-read prompt collection :marked-candidates t - :name name - :buffer buffer)) - - (add-to-list 'helm-completing-read-handlers-alist - '(foo/test . helm-foo/test-completing-read-handler)) - - -We want here to make the regular `completing-read' in `foo/test' -returns a list of candidate(s) instead of a single candidate. - -Note that this function will be reused for ALL the `completing-read' -of this command, so it should handle all cases, e.g -If first `completing-read' complete against symbols and -second `completing-read' should handle only buffer, -your specialized function should handle the both. - -If the value of an entry is nil completion will fall back to -emacs vanilla behavior. -Example: - -If you want to disable helm completion for `describe-function', use: - - (describe-function . nil) - -Ido is also supported, you can use `ido-completing-read' and -`ido-read-file-name' as value of an entry or just 'ido. -Example: -Enable ido completion for `find-file': - - (find-file . ido) - -same as - - (find-file . ido-read-file-name) - -Note that you don't need to enable `ido-mode' for this to work, see -`helm-mode' documentation." - :group 'helm-mode - :type '(alist :key-type symbol :value-type symbol)) - -(defcustom helm-comp-read-case-fold-search helm-case-fold-search - "Default Local setting of `helm-case-fold-search' for `helm-comp-read'. -See `helm-case-fold-search' for more info." - :group 'helm-mode - :type 'symbol) - -(defcustom helm-mode-handle-completion-in-region t - "Whether to replace or not `completion-in-region-function'. -This enable support for `completing-read-multiple' and `completion-at-point' -when non--nil." - :group 'helm-mode - :type 'boolean) - -(defcustom helm-mode-reverse-history t - "Display history source after current source in `helm-mode' handled commands." - :group 'helm-mode - :type 'boolean) - -(defcustom helm-mode-no-completion-in-region-in-modes nil - "A list of modes that do not want helm for `completion-in-region'." - :group 'helm-mode - :type 'boolean) - -(defcustom helm-completion-in-region-default-sort-fn - 'helm-completion-in-region-sort-fn - "The default sort function to sort candidates in completion-in-region. - -When nil no sorting is done. -The function is a `filtered-candidate-transformer' function which takes -two args CANDIDATES and SOURCE. -It will be used only when `helm-completion-style' is either emacs or -helm, otherwise when helm-fuzzy style is used, the fuzzy sort function -will be used." - :group 'helm-mode - :type 'function) - -(defcustom helm-mode-fuzzy-match nil - "Enable fuzzy matching in `helm-mode' globally. -Note that this will slow down completion and modify sorting -which is unwanted in many places. -This affect only the functions with completing-read helmized by helm-mode. -To fuzzy match `completion-at-point' and friends see -`helm-completion-style'." - :group 'helm-mode - :type 'boolean) - -(defcustom helm-mode-minibuffer-setup-hook-black-list '(minibuffer-completion-help) - "Incompatible `minibuffer-setup-hook' functions go here. -A list of symbols. -Helm-mode is rejecting all lambda's, byte-code fns -and all functions belonging in this list from `minibuffer-setup-hook'." - :group 'helm-mode - :type '(repeat (choice symbol))) - -(defcustom helm-completing-read-dynamic-complete nil - "Use dynamic completion in `completing-read' when non-nil. - -The default is to not use this because it is most of the time unneeded -in `completing-read' and thus it is much more slower. -If you feel one emacs function need this you have better time to tell -`helm-mode' to use a dynamic completion for this function only by using -`helm-completing-read-handlers-alist' with an entry like this: - - (my-function . helm-completing-read-sync-default-handler) - -So you should not change the default setting of this variable unless you -know what you are doing." - :group 'helm-mode - :type 'boolean) - -(defface helm-mode-prefix - '((t (:background "red" :foreground "black"))) - "Face used for prefix completion." - :group 'helm-mode) - -(defvar helm-comp-read-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "") 'helm-cr-empty-string) - (define-key map (kbd "M-RET") 'helm-cr-empty-string) - map) - "Keymap for `helm-comp-read'.") - -(defun helm-mode-delete-char-backward-1 () - (interactive) - (condition-case err - (call-interactively 'delete-backward-char) - (text-read-only - (if (with-selected-window (minibuffer-window) - (not (string= (minibuffer-contents) ""))) - (message "Trying to delete prefix completion, next hit will quit") - (user-error "%s" (car err)))))) -(put 'helm-mode-delete-char-backward-1 'helm-only t) - -(defun helm-mode-delete-char-backward-2 () - (interactive) - (condition-case _err - (call-interactively 'delete-backward-char) - (text-read-only - (unless (with-selected-window (minibuffer-window) - (string= (minibuffer-contents) "")) - (with-helm-current-buffer - (run-with-timer 0.1 nil (lambda () - (call-interactively 'delete-backward-char)))) - (helm-keyboard-quit))))) -(put 'helm-mode-delete-char-backward-2 'helm-only t) - -(helm-multi-key-defun helm-mode-delete-char-backward-maybe - "Delete char backward when text is not the prefix helm is completing against. -First call warn user about deleting prefix completion. -Second call delete backward char in current-buffer and quit helm completion, -letting user starting a new completion with a new prefix." - '(helm-mode-delete-char-backward-1 helm-mode-delete-char-backward-2) 1) - -(defcustom helm-completion-style 'emacs - "Style of completion to use in `completion-in-region'. - -This affect only `completion-at-point' and friends, NOT -`completing-read' nor other helm commands. - -NB: This have nothing to do with `completion-styles', it is independent to -helm. - -There is three possible value to use: -- helm, use multi match regular helm completion. -- helm-fuzzy, use fuzzy matching, note that as usual when - entering a space helm switch to multi matching mode. -- emacs, use regular emacs completion according to - `completion-styles', note that even in this style, helm allow using - multi match. Emacs-27 provide a style called flex that can be used - along this helm style (see `completion-styles-alist'). - -Please use custom interface or `customize-set-variable' to set this, -NOT `setq'." - :group 'helm-mode - :type '(choice (const :tag "Emacs" emacs) - (const :tag "Helm" helm) - (const :tag "Helm-fuzzy" helm-fuzzy)) - :set (lambda (var val) - (set var val) - (if (memq val '(helm helm-fuzzy)) - (define-key helm-comp-read-map (kbd "DEL") 'helm-mode-delete-char-backward-maybe) - (define-key helm-comp-read-map (kbd "DEL") 'delete-backward-char)))) - -(defcustom helm-completion-styles-alist '((eshell-mode . helm)) - "Allow configuring `helm-completion-style' per mode. - -Each entry is a cons cell like (mode . style) where style must be a -suitable value for `helm-completion-style'." - :group 'helm-mode - :type '(alist :key-type (symbol :tag "Mode") - :value-type (symbol :tag "Style"))) - -;;; helm-comp-read -;; -;; -(defun helm-cr-empty-string () - "Return empty string." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action - (lambda (_candidate) - (identity ""))))) -(put 'helm-cr-empty-string 'helm-only t) - -(defun helm-mode--keyboard-quit () - ;; Use this instead of `keyboard-quit' - ;; to avoid deactivating mark in current-buffer. - (let ((debug-on-quit nil)) - (signal 'quit nil))) - -(cl-defun helm-comp-read-get-candidates (collection &optional - test sort-fn alistp - (input helm-pattern)) - "Convert COLLECTION to list removing elements that don't match TEST. -See `helm-comp-read' about supported COLLECTION arguments. - -SORT-FN is a predicate to sort COLLECTION. - -ALISTP when non--nil will not use `all-completions' to collect -candidates because it doesn't handle alists correctly for helm. -i.e In `all-completions' the car of each pair is used as value. -In helm we want to use the cdr instead like \(display . real\), -so we return the alist as it is with no transformation by -`all-completions'. - -e.g - -\(setq A '((a . 1) (b . 2) (c . 3))) -==>((a . 1) (b . 2) (c . 3)) -\(helm-comp-read \"test: \" A :alistp nil - :exec-when-only-one t - :initial-input \"a\") -==>\"a\" Which is not what we expect. - -\(helm-comp-read \"test: \" A :alistp t - :exec-when-only-one t - :initial-input \"1\") -==>\"1\" - -See docstring of `all-completions' for more info. - -INPUT is the string you want to complete against, defaulting to -`helm-pattern' which is the value of what you enter in minibuffer. -Note that when using a function as COLLECTION this value will be -available with the input argument of the function only when using a -sync source from `helm-comp-read', i.e not using -`:candidates-in-buffer', otherwise the function is called only once -with an empty string as value for `helm-pattern' because -`helm-pattern' is not yet computed, which is what we want otherwise -data would not be fully collected at init time. - -If COLLECTION is an `obarray', a TEST should be needed. See `obarray'." - ;; Ensure COLLECTION is computed from `helm-current-buffer' - ;; because some functions used as COLLECTION work - ;; only in the context of current-buffer (Issue #1030) . - (with-helm-current-buffer - (let ((cands - (cond ((vectorp collection) - (all-completions input collection test)) - ((and (symbolp collection) (boundp collection) - ;; Issue #324 history is let-bounded and given - ;; quoted as hist argument of completing-read. - ;; See example in `rcirc-browse-url'. - (symbolp (symbol-value collection))) - nil) - ;; When collection is a symbol, most of the time - ;; it should be a symbol used as a minibuffer-history. - ;; The value of this symbol in this case return a list - ;; of string which maybe are converted later as symbol - ;; in special cases. - ;; we treat here commandp as a special case as it return t - ;; also with a string unless its last arg is provided. - ;; Also, the history collections generally collect their - ;; elements as string, so intern them to call predicate. - ((and (symbolp collection) (boundp collection) test) - (let ((predicate (lambda (elm) - (condition-case _err - (if (eq test 'commandp) - (funcall test (intern elm)) - (funcall test elm)) - (wrong-type-argument - (funcall test (intern elm))))))) - (all-completions input (symbol-value collection) predicate))) - ((and (symbolp collection) (boundp collection)) - (all-completions input (symbol-value collection))) - ;; Normally file completion should not be handled here, - ;; but special cases like `find-file-at-point' do it. - ;; Handle here specially such cases. - ((and (functionp collection) (not (string= input "")) - minibuffer-completing-file-name) - (cl-loop for f in (funcall collection input test) - unless (member f '("./" "../")) - if (string-match helm--url-regexp input) - collect f - else - collect (concat (file-name-as-directory - (helm-basedir input)) - f))) - ((functionp collection) - (funcall collection input test t)) - ((and alistp (null test)) collection) - ;; Next test ensure circular objects are removed - ;; with `all-completions' (Issue #1530). - (t (all-completions input collection test))))) - (if sort-fn (sort cands sort-fn) cands)))) - -(defun helm-cr--pattern-in-candidates-p (candidates) - (or (assoc helm-pattern candidates) - (assq (intern helm-pattern) candidates) - (member helm-pattern candidates) - (member (downcase helm-pattern) candidates) - (member (upcase helm-pattern) candidates))) - -(defun helm-cr-default-transformer (candidates source) - "Default filter candidate function for `helm-comp-read'." - (let ((must-match (helm-attr 'must-match source)) - unknown-pattern) - (unless (or (eq must-match t) - (string= helm-pattern "") - (helm-cr--pattern-in-candidates-p candidates)) - (setq candidates (append (list - ;; Unquote helm-pattern - ;; when it is added - ;; as candidate: Why? #2015 - ;; (replace-regexp-in-string - ;; "\\s\\" "" helm-pattern) - helm-pattern) - candidates)) - ;; Notify pattern have been added to candidates. - (setq unknown-pattern t)) - (cl-loop for c in candidates - for cand = (if (stringp c) - (replace-regexp-in-string "\\s\\" "" c) - c) - for pat = (replace-regexp-in-string "\\s\\" "" helm-pattern) - if (and (or (equal c pat) (equal c helm-pattern)) - unknown-pattern) - collect - (cons (concat (propertize - " " 'display - (propertize "[?]" 'face 'helm-ff-prefix)) - c) - c) - into lst - else collect (if (and (stringp cand) - (string-match "\n" cand)) - (cons (replace-regexp-in-string "\n" "->" c) c) - c) - into lst - finally return (helm-fast-remove-dups lst :test 'equal)))) - -(defun helm-comp-read--move-to-first-real-candidate () - (helm-aif (helm-get-selection nil 'withprop) - (when (string= (get-text-property 0 'display it) "[?]") - (helm-next-line)))) - -(defun helm-cr-default (default cands) - (delq nil - (cond ((and (stringp default) (not (string= default ""))) - (cons default (delete default cands))) - ((consp default) - (append (cl-loop for d in default - ;; Don't convert - ;; nil to "nil" (i.e the string) - ;; it will be delq'ed on top. - collect (if (null d) d (helm-stringify d))) - cands)) - (t cands)))) - -;;;###autoload -(cl-defun helm-comp-read (prompt collection - &key - test - initial-input - default - preselect - (buffer "*Helm Completions*") - must-match - fuzzy - reverse-history - (requires-pattern 0) - history - input-history - (case-fold helm-comp-read-case-fold-search) - (del-input t) - (persistent-action nil) - (persistent-help "DoNothing") - (mode-line helm-comp-read-mode-line) - help-message - (keymap helm-comp-read-map) - (name "Helm Completions") - header-name - candidates-in-buffer - match-part - match-dynamic - exec-when-only-one - quit-when-no-cand - (volatile t) - sort - fc-transformer - hist-fc-transformer - marked-candidates - nomark - (alistp t) - (candidate-number-limit helm-candidate-number-limit) - multiline - allow-nest - (group 'helm)) - "Read a string in the minibuffer, with helm completion. - -It is helm `completing-read' equivalent. - -- PROMPT is the prompt name to use. - -- COLLECTION can be a list, vector, obarray or hash-table. - It can be also a function that receives three arguments: - the values string, predicate and t. See `all-completions' for more details. - -Keys description: - -- TEST: A predicate called with one arg i.e candidate. - -- INITIAL-INPUT: Same as input arg in `helm'. - -- PRESELECT: See preselect arg of `helm'. - -- DEFAULT: This option is used only for compatibility with regular - Emacs `completing-read' (Same as DEFAULT arg of `completing-read'). - -- BUFFER: Name of helm-buffer. - -- MUST-MATCH: Candidate selected must be one of COLLECTION. - -- FUZZY: Enable fuzzy matching. - -- REVERSE-HISTORY: When non--nil display history source after current - source completion. - -- REQUIRES-PATTERN: Same as helm attribute, default is 0. - -- HISTORY: A list containing specific history, default is nil. - When it is non--nil, all elements of HISTORY are displayed in - a special source before COLLECTION. - -- INPUT-HISTORY: A symbol. the minibuffer input history will be - stored there, if nil or not provided, `minibuffer-history' - will be used instead. - -- CASE-FOLD: Same as `helm-case-fold-search'. - -- DEL-INPUT: Boolean, when non--nil (default) remove the partial - minibuffer input from HISTORY is present. - -- PERSISTENT-ACTION: A function called with one arg i.e candidate. - -- PERSISTENT-HELP: A string to document PERSISTENT-ACTION. - -- MODE-LINE: A string or list to display in mode line. - Default is `helm-comp-read-mode-line'. - -- KEYMAP: A keymap to use in this `helm-comp-read'. - (the keymap will be shared with history source) - -- NAME: The name related to this local source. - -- HEADER-NAME: A function to alter NAME, see `helm'. - -- EXEC-WHEN-ONLY-ONE: Bound `helm-execute-action-at-once-if-one' - to non--nil. (possibles values are t or nil). - -- VOLATILE: Use volatile attribute. - -- SORT: A predicate to give to `sort' e.g `string-lessp' - Use this only on small data as it is ineficient. - If you want to sort faster add a sort function to - FC-TRANSFORMER. - Note that FUZZY when enabled is already providing a sort function. - -- FC-TRANSFORMER: A `filtered-candidate-transformer' function - or a list of functions. - -- HIST-FC-TRANSFORMER: A `filtered-candidate-transformer' - function for the history source. - -- MARKED-CANDIDATES: If non--nil return candidate or marked candidates as a list. - -- NOMARK: When non--nil don't allow marking candidates. - -- ALISTP: (default is non--nil) See `helm-comp-read-get-candidates'. - -- CANDIDATES-IN-BUFFER: when non--nil use a source build with - `helm-source-in-buffer' which is much faster. - Argument VOLATILE have no effect when CANDIDATES-IN-BUFFER is non--nil. - -- MATCH-PART: Allow matching only one part of candidate. - See match-part documentation in `helm-source'. - -- MATCH-DYNAMIC: See match-dynamic in `helm-source-sync' - It have no effect when used with CANDIDATES-IN-BUFFER. - -- ALLOW-NEST: Allow nesting this `helm-comp-read' in a helm session. - See `helm'. - -- MULTILINE: See multiline in `helm-source'. - -- GROUP: See group in `helm-source'. - -Any prefix args passed during `helm-comp-read' invocation will be recorded -in `helm-current-prefix-arg', otherwise if prefix args were given before -`helm-comp-read' invocation, the value of `current-prefix-arg' will be used. -That's mean you can pass prefix args before or after calling a command -that use `helm-comp-read' See `helm-M-x' for example." - - (when (get-buffer helm-action-buffer) - (kill-buffer helm-action-buffer)) - (let ((action-fn `(("Sole action (Identity)" - . (lambda (candidate) - (if ,marked-candidates - (helm-marked-candidates) - (identity candidate))))))) - ;; Assume completion have been already required, - ;; so always use 'confirm. - (when (eq must-match 'confirm-after-completion) - (setq must-match 'confirm)) - (let* ((minibuffer-completion-confirm must-match) - (must-match-map (when must-match - (let ((map (make-sparse-keymap))) - (define-key map (kbd "RET") - 'helm-confirm-and-exit-minibuffer) - map))) - (loc-map (if must-match-map - (make-composed-keymap - must-match-map (or keymap helm-map)) - (or keymap helm-map))) - (minibuffer-completion-predicate test) - (minibuffer-completion-table collection) - (helm-read-file-name-mode-line-string - (replace-regexp-in-string "helm-maybe-exit-minibuffer" - "helm-confirm-and-exit-minibuffer" - helm-read-file-name-mode-line-string)) - (get-candidates - (lambda () - (let ((cands (helm-comp-read-get-candidates - ;; If `helm-pattern' is passed as INPUT - ;; and :alistp is nil INPUT is passed to - ;; `all-completions' which defeat helm - ;; matching functions (multi match, fuzzy - ;; etc...) issue #2134. - collection test sort alistp - (if (and match-dynamic (null candidates-in-buffer)) - helm-pattern "")))) - (helm-cr-default default cands)))) - (history-get-candidates - (lambda () - (let ((cands (helm-comp-read-get-candidates - history test nil alistp))) - (when cands - (delete "" (helm-cr-default default cands)))))) - (src-hist (helm-build-sync-source (format "%s History" name) - :candidates history-get-candidates - :fuzzy-match fuzzy - :multiline multiline - :match-part match-part - :filtered-candidate-transformer - (append '((lambda (candidates sources) - (cl-loop for i in candidates - ;; Input is added to history in completing-read's - ;; and may be regexp-quoted, so unquote it - ;; but check if cand is a string (it may be at this stage - ;; a symbol or nil) Issue #1553. - when (stringp i) - collect (replace-regexp-in-string "\\s\\" "" i)))) - (and hist-fc-transformer (helm-mklist hist-fc-transformer))) - :persistent-action persistent-action - :persistent-help persistent-help - :keymap loc-map - :group group - :mode-line mode-line - :help-message help-message - :action action-fn)) - (src (helm-build-sync-source name - :candidates get-candidates - :match-part match-part - :multiline multiline - :header-name header-name - :filtered-candidate-transformer - (let ((transformers (helm-mklist fc-transformer))) - (append transformers - (unless (member 'helm-cr-default-transformer transformers) - '(helm-cr-default-transformer)))) - :requires-pattern requires-pattern - :persistent-action persistent-action - :persistent-help persistent-help - :fuzzy-match fuzzy - :keymap loc-map - :group group - :mode-line mode-line - :match-dynamic match-dynamic - :help-message help-message - :action action-fn - :volatile volatile)) - (src-1 (helm-build-in-buffer-source name - :data get-candidates - :match-part match-part - :multiline multiline - :header-name header-name - :filtered-candidate-transformer - (append (helm-mklist fc-transformer) - '(helm-cr-default-transformer)) - :requires-pattern requires-pattern - :persistent-action persistent-action - :fuzzy-match fuzzy - :keymap loc-map - :group group - :persistent-help persistent-help - :mode-line mode-line - :help-message help-message - :action action-fn)) - (src-list (list src-hist - (cons (cons 'must-match must-match) - (if candidates-in-buffer - src-1 src)))) - (helm-execute-action-at-once-if-one exec-when-only-one) - (helm-quit-if-no-candidate quit-when-no-cand) - result) - (when nomark - (setq src-list (cl-loop for src in src-list - collect (cons '(nomark) src)))) - (when reverse-history (setq src-list (nreverse src-list))) - (add-hook 'helm-after-update-hook 'helm-comp-read--move-to-first-real-candidate) - (unwind-protect - (setq result (helm - :sources src-list - :input initial-input - :default default - :preselect preselect - :prompt prompt - :resume 'noresume - :keymap loc-map ;; Needed with empty collection. - :allow-nest allow-nest - :candidate-number-limit candidate-number-limit - :case-fold-search case-fold - :history (and (symbolp input-history) input-history) - :buffer buffer)) - (remove-hook 'helm-after-update-hook 'helm-comp-read--move-to-first-real-candidate)) - ;; Avoid adding an incomplete input to history. - (when (and result history del-input) - (cond ((and (symbolp history) ; History is a symbol. - (not (symbolp (symbol-value history)))) ; Fix Issue #324. - ;; Be sure history is not a symbol with a nil value. - (helm-aif (symbol-value history) (setcar it result))) - ((consp history) ; A list with a non--nil value. - (setcar history result)) - (t ; Possibly a symbol with a nil value. - (set history (list result))))) - (or result (helm-mode--keyboard-quit))))) - - -;; Generic completing-read -;; -;; Support also function as collection. -;; e.g M-x man is supported. -;; Support hash-table and vectors as collection. -;; NOTE: -;; Some crap emacs functions may not be supported -;; like ffap-alternate-file (bad use of completing-read) -;; and maybe others. -;; Provide a mode `helm-mode' which turn on -;; helm in all `completing-read' and `read-file-name' in Emacs. -;; -(defvar helm-completion-mode-string " Helm") - -(defvar helm-completion-mode-quit-message - "Helm completion disabled") - -(defvar helm-completion-mode-start-message - "Helm completion enabled") - -;;; Specialized handlers -;; -;; -(defun helm-completing-read-symbols - (prompt _collection test _require-match init - hist default _inherit-input-method name buffer) - "Specialized function for fast symbols completion in `helm-mode'." - (require 'helm-elisp) - (or - (helm - :sources (helm-build-in-buffer-source name - :init (lambda () - (helm-apropos-init (lambda (x) - (and (funcall test x) - (not (keywordp x)))) - (or (car-safe default) default))) - :filtered-candidate-transformer 'helm-apropos-default-sort-fn - :help-message #'helm-comp-read-help-message - :fuzzy-match helm-mode-fuzzy-match - :persistent-action - (lambda (candidate) - (helm-lisp-completion-persistent-action - candidate name)) - :persistent-help (helm-lisp-completion-persistent-help)) - :prompt prompt - :buffer buffer - :input init - :history hist - :resume 'noresume - :default (or default "")) - (helm-mode--keyboard-quit))) - - -;;; Generic completing read -;; -;; -(defun helm-completing-read-default-1 - (prompt collection test require-match - init hist default _inherit-input-method - name buffer &optional cands-in-buffer exec-when-only-one) - "Call `helm-comp-read' with same args as `completing-read'. -Extra optional arg CANDS-IN-BUFFER mean use `candidates-in-buffer' -method which is faster. -It should be used when candidate list don't need to rebuild dynamically." - (let ((history (or (car-safe hist) hist)) - (initial-input (helm-aif (pcase init - ((pred (stringp)) init) - ;; INIT is a cons cell. - (`(,l . ,_ll) l)) - it))) - (helm-comp-read - prompt collection - :test test - :history history - :reverse-history helm-mode-reverse-history - :input-history history - :must-match require-match - :alistp nil - :help-message #'helm-comp-read-help-message - :name name - :requires-pattern (if (and (stringp default) - (string= default "") - (or (eq require-match 'confirm) - (eq require-match - 'confirm-after-completion))) - 1 0) - :candidates-in-buffer cands-in-buffer - :exec-when-only-one exec-when-only-one - :fuzzy helm-mode-fuzzy-match - :buffer buffer - ;; If DEF is not provided, fallback to empty string - ;; to avoid `thing-at-point' to be appended on top of list - :default (or default "") - ;; Fail with special characters (e.g in gnus "nnimap+gmail:") - ;; if regexp-quote is not used. - ;; when init is added to history, it will be unquoted by - ;; helm-comp-read. - :initial-input initial-input))) - -(defun helm-completing-read-default-find-tag - (prompt collection test require-match - init hist default inherit-input-method - name buffer) - "Specialized `helm-mode' handler for `find-tag'." - ;; Some commands like find-tag may use `read-file-name' from inside - ;; the calculation of collection. in this case it clash with - ;; candidates-in-buffer that reuse precedent data (files) which is wrong. - ;; So (re)calculate collection outside of main helm-session. - (let* ((cands (helm-comp-read-get-candidates - collection test nil nil))) - (helm-completing-read-default-1 prompt cands test require-match - init hist default inherit-input-method - name buffer t))) - -(defun helm-completing-read-sync-default-handler - (prompt collection test require-match - init hist default inherit-input-method - name buffer) - "`helm-mode' handler using sync source as backend." - (helm-completing-read-default-1 prompt collection test require-match - init hist default inherit-input-method - name buffer)) - -(defun helm-completing-read-default-handler - (prompt collection test require-match - init hist default inherit-input-method - name buffer) - "Default `helm-mode' handler for all `completing-read'." - (helm-completing-read-default-1 prompt collection test require-match - init hist default inherit-input-method - name buffer - (null helm-completing-read-dynamic-complete))) - -(defun helm--generic-read-buffer (prompt &optional default require-match predicate) - "The `read-buffer-function' for `helm-mode'. -Affects `switch-to-buffer' and related." - (let ((collection (helm-buffer-list))) - (helm--completing-read-default - prompt collection predicate require-match nil nil default))) - -(cl-defun helm--completing-read-default - (prompt collection &optional - predicate require-match - initial-input hist def - inherit-input-method) - "An helm replacement of `completing-read'. -This function should be used only as a `completing-read-function'. - -Don't use it directly, use instead `helm-comp-read' in your programs. - -See documentation of `completing-read' and `all-completions' for details." - (let* ((current-command (or (helm-this-command) this-command)) - (str-command (helm-symbol-name current-command)) - (buf-name (format "*helm-mode-%s*" str-command)) - (entry (assq current-command - helm-completing-read-handlers-alist)) - (def-com (cdr-safe entry)) - (str-defcom (and def-com (helm-symbol-name def-com))) - (def-args (list prompt collection predicate require-match - initial-input hist def inherit-input-method)) - ;; Append the two extra args needed to set the buffer and source name - ;; in helm specialized functions. - (any-args (append def-args (list str-command buf-name))) - helm-completion-mode-start-message ; Be quiet - helm-completion-mode-quit-message - ;; Be sure this pesty *completion* buffer doesn't popup. - ;; Note: `minibuffer-with-setup-hook' may setup a lambda - ;; calling `minibuffer-completion-help' or other minibuffer - ;; functions we DONT WANT here, in these cases removing the hook - ;; (a symbol) have no effect. Issue #448. - ;; Because `minibuffer-completion-table' and - ;; `minibuffer-completion-predicate' are not bound - ;; anymore here, these functions should have no effect now, - ;; except in some rare cases like in `woman-file-name', - ;; so remove all incompatible functions - ;; from `minibuffer-setup-hook' (Issue #1205, #1240). - ;; otherwise helm have not the time to close its initial session. - (minibuffer-setup-hook - (cl-loop for h in minibuffer-setup-hook - unless (or (consp h) ; a lambda. - (byte-code-function-p h) - (memq h helm-mode-minibuffer-setup-hook-black-list)) - collect h)) - ;; Disable hack that could be used before `completing-read'. - ;; i.e (push ?\t unread-command-events). - unread-command-events - (default-handler - ;; Typically when COLLECTION is a function, we can assume - ;; the intention is completing dynamically according to - ;; input; If one want to use in-buffer handler for specific - ;; usage with a function as collection he can specify it in - ;; helm-completing-read-handlers-alist. - (if (functionp collection) - #'helm-completing-read-sync-default-handler - #'helm-completing-read-default-handler))) - (when (eq def-com 'ido) (setq def-com 'ido-completing-read)) - (unless (or (not entry) def-com) - ;; An entry in *read-handlers-alist exists but have - ;; a nil value, so we exit from here, disable `helm-mode' - ;; and run the command again with it original behavior. - ;; `helm-mode' will be restored on exit. - (cl-return-from helm--completing-read-default - (unwind-protect - (progn - (helm-mode -1) - (apply completing-read-function def-args)) - (helm-mode 1)))) - ;; If we use now `completing-read' we MUST turn off `helm-mode' - ;; to avoid infinite recursion and CRASH. It will be reenabled on exit. - (when (or (eq def-com 'completing-read) - ;; All specialized functions are prefixed by "helm" - (and (stringp str-defcom) - (not (string-match "^helm" str-defcom)))) - (helm-mode -1)) - (unwind-protect - (cond (;; An helm specialized function exists, run it. - (and def-com helm-mode) - (apply def-com any-args)) - (;; Try to handle `ido-completing-read' everywhere. - (and def-com (eq def-com 'ido-completing-read)) - (setcar (memq collection def-args) - (all-completions "" collection predicate)) - (apply def-com def-args)) - (;; User set explicitely `completing-read' or something similar - ;; in *read-handlers-alist, use this with exactly the same - ;; args as in `completing-read'. - ;; If we are here `helm-mode' is now disabled. - def-com - (apply def-com def-args)) - (;; Use by default a in-buffer handler unless - ;; COLLECTION is a function. - t - (funcall default-handler - prompt collection predicate require-match - initial-input hist def inherit-input-method - str-command buf-name))) - (helm-mode 1) - ;; When exiting minibuffer, `this-command' is set to - ;; `helm-exit-minibuffer', which is unwanted when starting - ;; on another `completing-read', so restore `this-command' to - ;; initial value when exiting. - (setq this-command current-command)))) - -;;; Generic read-file-name -;; -;; -;;;###autoload -(cl-defun helm-read-file-name - (prompt - &key - (name "Read File Name") - (initial-input default-directory) - (buffer "*Helm file completions*") - test - noret - (case-fold helm-file-name-case-fold-search) - preselect - history - must-match - (fuzzy t) - default - marked-candidates - (candidate-number-limit helm-ff-candidate-number-limit) - nomark - (alistp t) - (persistent-action-if 'helm-find-files-persistent-action-if) - (persistent-help "Hit1 Expand Candidate, Hit2 or (C-u) Find file") - (mode-line helm-read-file-name-mode-line-string)) - "Read a file name with helm completion. -It is helm `read-file-name' emulation. - -Argument PROMPT is the default prompt to use. - -Keys description: - -- NAME: Source name, default to \"Read File Name\". - -- INITIAL-INPUT: Where to start read file name, default to `default-directory'. - -- BUFFER: `helm-buffer' name default to \"*Helm Completions*\". - -- TEST: A predicate called with one arg 'candidate'. - -- NORET: Allow disabling helm-ff-RET (have no effect if helm-ff-RET - isn't bound to RET). - -- CASE-FOLD: Same as `helm-case-fold-search'. - -- PRESELECT: helm preselection. - -- HISTORY: Display HISTORY in a special source. - -- MUST-MATCH: Can be 'confirm, nil, or t. - -- FUZZY: Enable fuzzy matching when non-nil (Enabled by default). - -- MARKED-CANDIDATES: When non--nil return a list of marked candidates. - -- NOMARK: When non--nil don't allow marking candidates. - -- ALISTP: Don't use `all-completions' in history (take effect only on history). - -- PERSISTENT-ACTION-IF: a persistent if action function. - -- PERSISTENT-HELP: persistent help message. - -- MODE-LINE: A mode line message, default is `helm-read-file-name-mode-line-string'." - (require 'tramp) - (when (get-buffer helm-action-buffer) - (kill-buffer helm-action-buffer)) - ;; Assume completion have been already required, - ;; so always use 'confirm. - (when (eq must-match 'confirm-after-completion) - (setq must-match 'confirm)) - (mapc (lambda (hook) - (add-hook 'helm-after-update-hook hook)) - '(helm-ff-move-to-first-real-candidate - helm-ff-update-when-only-one-matched - helm-ff-auto-expand-to-home-or-root)) - (let* ((action-fn `(("Sole action (Identity)" - . (lambda (candidate) - (if ,marked-candidates - (helm-marked-candidates :with-wildcard t) - (identity candidate)))))) - ;; Be sure we don't erase the underlying minibuffer if some. - (helm-ff-auto-update-initial-value - (and helm-ff-auto-update-initial-value - (not (minibuffer-window-active-p (minibuffer-window))))) - helm-follow-mode-persistent - (helm-ff-fuzzy-matching - (and fuzzy - (not (memq helm-mm-matching-method '(multi1 multi3p))))) - (hist (and history (helm-comp-read-get-candidates - history nil nil alistp))) - (minibuffer-completion-confirm must-match) - (helm-ff--RET-disabled noret) - (must-match-map (when must-match - (let ((map (make-sparse-keymap))) - (define-key map (kbd "RET") - (let ((fn (lookup-key helm-read-file-map (kbd "RET")))) - (if (and (eq fn 'helm-ff-RET) - (null helm-ff--RET-disabled)) - #'helm-ff-RET-must-match - #'helm-confirm-and-exit-minibuffer))) - map))) - (cmap (if must-match-map - (make-composed-keymap - must-match-map helm-read-file-map) - helm-read-file-map)) - (minibuffer-completion-predicate test) - (minibuffer-completing-file-name t) - (helm--completing-file-name t) - (helm-read-file-name-mode-line-string - (replace-regexp-in-string "helm-maybe-exit-minibuffer" - "helm-confirm-and-exit-minibuffer" - helm-read-file-name-mode-line-string)) - (src-list - (list - ;; History source. - (helm-build-sync-source (format "%s History" name) - :header-name (lambda (name) - (concat name (substitute-command-keys - helm-find-files-doc-header))) - :mode-line mode-line - :candidates hist - :nohighlight t - :fuzzy-match fuzzy - :persistent-action-if persistent-action-if - :persistent-help persistent-help - :keymap cmap - :nomark nomark - :action action-fn) - ;; Other source. - (helm-build-sync-source name - :header-name (lambda (name) - (concat name (substitute-command-keys - helm-find-files-doc-header))) - :init (lambda () - (setq helm-ff-auto-update-flag - helm-ff-auto-update-initial-value) - (setq helm-ff--auto-update-state - helm-ff-auto-update-flag)) - :mode-line mode-line - :help-message 'helm-read-file-name-help-message - :nohighlight t - :candidates - (lambda () - (append (and (not (file-exists-p helm-pattern)) - (not (helm-ff--invalid-tramp-name-p helm-pattern)) - (list helm-pattern)) - (if test - (cl-loop with hn = (helm-ff--tramp-hostnames) - for i in (helm-find-files-get-candidates - must-match) - when (or (member i hn) ; A tramp host - (funcall test i)) ; Test ok - collect i) - (helm-find-files-get-candidates must-match)))) - :filtered-candidate-transformer 'helm-ff-sort-candidates - :filter-one-by-one 'helm-ff-filter-candidate-one-by-one - :persistent-action-if persistent-action-if - :persistent-help persistent-help - :volatile t - :keymap cmap - :cleanup 'helm-find-files-cleanup - :nomark nomark - :action action-fn))) - ;; Helm result. - (result (helm - :sources (if helm-mode-reverse-history - (reverse src-list) src-list) - :input (expand-file-name initial-input) - :prompt prompt - :candidate-number-limit candidate-number-limit - :resume 'noresume - :case-fold-search case-fold - :default default - :buffer buffer - :full-frame nil - :preselect preselect))) - (or - (cond ((and result (stringp result) - (string= result "") "")) - ((and result - (stringp result) - (file-equal-p result initial-input) - default) - (if (listp default) (car default) default)) - ((and result (listp result)) - (mapcar #'expand-file-name result)) - ((and result (file-directory-p result)) - (file-name-as-directory (expand-file-name result))) - (result (expand-file-name result))) - (helm-mode--keyboard-quit)))) - -(defun helm-mode--default-filename (fname dir initial) - (unless dir (setq dir default-directory)) - (unless (file-name-absolute-p dir) - (setq dir (expand-file-name dir))) - (unless (or fname (consp fname)) - (setq fname (expand-file-name - (or initial buffer-file-name dir) - dir))) - (if (and fname (consp fname)) - (setq fname (cl-loop for f in fname - collect (expand-file-name f dir))) - (if (file-name-absolute-p fname) - fname (expand-file-name fname dir)))) - -(cl-defun helm--generic-read-file-name - (prompt &optional dir default-filename mustmatch initial predicate) - "Generic helm replacement of `read-file-name'. -Don't use it directly, use instead `helm-read-file-name' in your programs." - (let* ((init (or initial dir default-directory)) - (current-command (or (helm-this-command) this-command)) - (str-command (helm-symbol-name current-command)) - (helm--file-completion-sources - (cons str-command - (remove str-command helm--file-completion-sources))) - (buf-name (format "*helm-mode-%s*" str-command)) - (entry (assq current-command - helm-completing-read-handlers-alist)) - (def-com (cdr-safe entry)) - (str-defcom (and def-com (helm-symbol-name def-com))) - ;; Don't modify the original args list for emacs generic functions. - (def-args (list prompt dir default-filename mustmatch initial predicate)) - ;; Append the two extra args needed to set the buffer and source name - ;; in helm specialized functions. - (any-args (append def-args (list str-command buf-name))) - (reading-directory (eq predicate 'file-directory-p)) - helm-completion-mode-start-message ; Be quiet - helm-completion-mode-quit-message ; Same here - fname) - ;; Build `default-filename' with `dir'+`initial' when - ;; `default-filename' is not specified. - ;; See `read-file-name' docstring for more infos. - (setq default-filename (helm-mode--default-filename - default-filename dir initial)) - ;; Some functions that normally call `completing-read' can switch - ;; brutally to `read-file-name' (e.g find-tag), in this case - ;; the helm specialized function will fail because it is build - ;; for `completing-read', so set it to 'incompatible to be sure - ;; we switch to `helm-read-file-name' and don't try to call it - ;; with wrong number of args. - (when (eq def-com 'ido) - (setq def-com 'ido-read-file-name)) - (when (and def-com (> (length (help-function-arglist def-com)) 8)) - (setq def-com 'incompatible)) - (unless (or (not entry) def-com) - (cl-return-from helm--generic-read-file-name - (unwind-protect - (progn - (helm-mode -1) - (apply read-file-name-function def-args)) - (helm-mode 1)))) - ;; If we use now `read-file-name' we MUST turn off `helm-mode' - ;; to avoid infinite recursion and CRASH. It will be reenabled on exit. - (when (or (eq def-com 'read-file-name) - (eq def-com 'ido-read-file-name) - (and (stringp str-defcom) - (not (string-match "^helm" str-defcom)))) - (helm-mode -1)) - (unwind-protect - (setq fname - (cond (;; A specialized function exists, run it - ;; with the two extra args specific to helm. - ;; Note that the helm handler should ensure - ;; :initial-input is not nil i.e. Use init - ;; which fallback to default-directory instead - ;; of INITIAL. - (and def-com helm-mode - (not (eq def-com 'ido-read-file-name)) - (not (eq def-com 'incompatible))) - (apply def-com any-args)) - (;; Def-com value is `ido-read-file-name' - ;; run it with default args. - (and def-com (eq def-com 'ido-read-file-name)) - (ido-mode 1) - (apply def-com def-args)) - (;; Def-com value is `read-file-name' - ;; run it with default args. - (eq def-com 'read-file-name) - (apply def-com def-args)) - (t ; Fall back to classic `helm-read-file-name'. - (helm-read-file-name - prompt - :name str-command - :buffer buf-name - :default default-filename - ;; Helm handlers should always have a non nil INITIAL arg. - :initial-input (expand-file-name init dir) - :alistp nil - :must-match mustmatch - :test predicate - :noret reading-directory)))) - (and ido-mode (ido-mode -1)) - (helm-mode 1) - ;; Same comment as in `helm--completing-read-default'. - (setq this-command current-command)) - (if (and - ;; Using `read-directory-name'. - reading-directory - ;; `file-name-as-directory' return "./" when FNAME is - ;; empty string. - (not (string= fname ""))) - (file-name-as-directory fname) fname))) - -;; Read file name handler with history (issue #1652) -(defun helm-read-file-name-handler-1 (prompt dir default-filename - mustmatch initial predicate - name buffer) - "A `read-file-name' handler with history. -Can be added to `helm-completing-read-handlers-alist' for functions -that need a `read-file-name' function with directory history. -The `helm-find-files' history `helm-ff-history' is used here." - (let ((helm-always-two-windows t) - (helm-split-window-default-side - (if (eq helm-split-window-default-side 'same) - 'below helm-split-window-default-side)) - helm-split-window-inside-p - helm-reuse-last-window-split-state - ;; Helm handlers should always have a non nil INITIAL arg. - (init (or initial dir default-directory))) - (helm-read-file-name - prompt - :name name - :history helm-ff-history - :buffer buffer - :default default-filename - :initial-input (expand-file-name init dir) - :alistp nil - :must-match mustmatch - :test predicate))) - - -;;; Completion in region and Helm style -;; -(defun helm-mode--advice-lisp--local-variables (old--fn &rest args) - (ignore-errors - (apply old--fn args))) - -(defvar helm-completion--sorting-done nil - "Flag that notify the FCT if sorting have been done in completion function.") -(defun helm-completion-in-region-sort-fn (candidates _source) - "Default sort function for completion-in-region." - (if helm-completion--sorting-done - candidates - (sort candidates 'helm-generic-sort-fn))) - -(defun helm-mode--completion-in-region-initial-input (str) - "Highlight prefix in helm and helm-fuzzy `helm-completion-styles'." - (if (memq helm-completion-style '(helm helm-fuzzy)) - (propertize str 'read-only t 'face 'helm-mode-prefix 'rear-nonsticky t) - str)) - -(defun helm-completion-try-completion (string table pred point) - "The try completion function for `completing-styles-alist'. -Actually do nothing." - ;; AFAIU the try completion function is here to handle single - ;; element completion, in this case it throw this element without - ;; popping up *completions* buffer. If that's the case we don't need - ;; this because helm already handle this with - ;; `helm-execute-action-at-once-if-one', so returning unconditionaly - ;; nil should be fine. - (ignore string table pred point)) - -(defun helm-completion-all-completions (string table pred point) - "The all completions function for `completing-styles-alist'." - ;; FIXME: No need to bind all these value. - (cl-multiple-value-bind (all _pattern prefix _suffix _carbounds) - (helm-completion--substring-all-completions string table pred point) - (when all (nconc all (length prefix))))) - -(defun helm-completion--all-completions-multi (string collection &optional predicate) - "Allow `all-completions' multi matching on its candidates." - (all-completions "" collection (lambda (x) - (if predicate - (and (funcall predicate x) - (helm-mm-match (helm-stringify x) string)) - (helm-mm-match (helm-stringify x) string))))) - -(defun helm-completion--substring-all-completions (string table pred point) - "Collect completions from TABLE for helm completion style." - (let* ((beforepoint (substring string 0 point)) - (afterpoint (substring string point)) - (bounds (completion-boundaries beforepoint table pred afterpoint)) - (prefix (substring beforepoint 0 (car bounds))) - (suffix (substring afterpoint (cdr bounds))) - (all (if (or (string-match-p " " string) - (string-match-p "\\`!" string)) - (helm-completion--all-completions-multi string table pred) - (all-completions string table pred)))) - (list all string prefix suffix point))) - -(defun helm-completion-in-region--initial-filter (comps afun file-comp-p) - "Add annotations at end of candidates and filter out dot files." - (if file-comp-p - ;; Filter out dot files in file completion. - (cl-loop for f in comps unless - (string-match "\\`\\.\\{1,2\\}/\\'" f) - collect f) - (if afun - ;; Add annotation at end of - ;; candidate if needed, e.g. foo, this happen when - ;; completing against a quoted symbol. - (mapcar (lambda (s) - (let ((ann (funcall afun s))) - (if ann - (cons - (concat - s - (propertize - " " 'display - (propertize - ann - 'face 'completions-annotations))) - s) - s))) - comps) - comps))) - -;; Setup completion styles for helm-mode -(defun helm-mode--setup-completion-styles () - (cl-pushnew '(helm helm-completion-try-completion - helm-completion-all-completions - "helm completion style.") - completion-styles-alist - :test 'equal)) - -(defun helm-mode--disable-completion-styles () - (setq completion-styles-alist - (delete (assq 'helm completion-styles-alist) - completion-styles-alist))) - -(defun helm-completion-in-region--fix-completion-styles () - "Add helm style to `completion-styles' and filter out invalid styles." - (if (memq helm-completion-style '(helm helm-fuzzy)) - '(basic partial-completion emacs22) - (cl-loop with all-styles = (mapcar 'car completion-styles-alist) - for style in (cons 'helm completion-styles) - when (and (memq style all-styles) - (not (memq style styles))) - collect style into styles - finally return styles))) - -(defun helm-completion--adjust-metadata (metadata) - (if (memq helm-completion-style '(helm helm-fuzzy)) - metadata - (cl-flet ((compose-helm-sort-fn - (_existing-sort-fn) - (lambda (candidates) - (let ((res candidates)) - (sort res #'helm-generic-sort-fn))))) - (let ((alist (cdr metadata))) - (helm-aif (assq 'display-sort-function alist) - (setq alist (remove it alist))) - `(metadata . ,(cons - (cons 'display-sort-function - (compose-helm-sort-fn - (alist-get 'display-sort-function alist))) - alist)))))) -(put 'helm 'completion--adjust-metadata 'helm-completion--adjust-metadata) - -(defun helm--completion-in-region (start end collection &optional predicate) - "Helm replacement of `completion--in-region'. -Can be used as value for `completion-in-region-function'." - (cl-declare (special require-match prompt)) - (if (memq major-mode helm-mode-no-completion-in-region-in-modes) - (funcall helm--old-completion-in-region-function - start end collection predicate) - (advice-add - 'lisp--local-variables - :around #'helm-mode--advice-lisp--local-variables) - (let ((old--helm-completion-style helm-completion-style)) - (helm-aif (cdr (assq major-mode helm-completion-styles-alist)) - (customize-set-variable 'helm-completion-style it)) - (unwind-protect - (let* ((enable-recursive-minibuffers t) - (completion-styles (helm-completion-in-region--fix-completion-styles)) - (input (buffer-substring start end)) - (current-command (or (helm-this-command) this-command)) - (crm (eq current-command 'crm-complete)) - (str-command (helm-symbol-name current-command)) - (buf-name (format "*helm-mode-%s*" str-command)) - (require-match (or (and (boundp 'require-match) require-match) - minibuffer-completion-confirm - ;; If prompt have not been propagated here, that's - ;; probably mean we have no prompt and we are in - ;; completion-at-point or friend, so use a non--nil - ;; value for require-match. - (not (boundp 'prompt)))) - ;; `completion-extra-properties' is let-bounded in `completion-at-point'. - ;; `afun' is a closure to call against each string in `data'. - ;; it provide the annotation info for each string. - ;; e.g "foo" => "foo " where foo is a function. - ;; See Issue #407. - (afun (plist-get completion-extra-properties :annotation-function)) - (metadata (completion-metadata - (buffer-substring start (point)) - collection predicate)) - (init-space-suffix (unless (or (memq helm-completion-style '(helm-fuzzy emacs)) - (string-suffix-p " " input) - (string= input "")) - " ")) - (file-comp-p (or (eq (completion-metadata-get metadata 'category) 'file) - (helm-mode--in-file-completion-p) - ;; Assume that when `afun' and `predicate' are null - ;; we are in filename completion. - (and (null afun) (null predicate)))) - ;; `completion-all-completions' store the base-size in the last `cdr', - ;; so data looks like this: '(a b c d . 0) and (last data) == (d . 0). - base-size - (compfn (lambda (str _predicate _action) - ;; Cache data for subsequent calls when emacs - ;; style is in use, with helm style function - ;; is called only once and cache is not - ;; needed but it doesn't harm to set hash, it - ;; will not be used. - (let* ((comps - (completion-all-completions - ;; `helm-comp-read-get-candidates' - ;; set input to `helm-pattern' - ;; so no need to pass - ;; `helm-pattern' directly here. - str - collection - predicate - (length str) - metadata)) - (last-data (last comps)) - (sort-fn (and (eq helm-completion-style 'emacs) - (completion-metadata-get - metadata 'display-sort-function))) - all) - (setq base-size - (helm-aif (cdr last-data) - (prog1 (or base-size it) - (setcdr last-data nil)) - 0)) - (setq helm-completion--sorting-done (and sort-fn t)) - (setq all (copy-sequence comps)) - ;; Fall back to string-lessp sorting when - ;; str is too small as specialized - ;; sorting may be too slow (flex). - (when (and sort-fn (<= (length str) 1)) - (setq sort-fn (lambda (all) (sort all #'string-lessp)))) - (helm-completion-in-region--initial-filter - (if sort-fn (funcall sort-fn all) all) - afun file-comp-p)))) - (data (if (memq helm-completion-style '(helm helm-fuzzy)) - (funcall compfn (buffer-substring start end) nil nil) - compfn)) - (result (if (stringp data) - data - (helm-comp-read - ;; Completion-at-point and friends have no prompt. - (or (and (boundp 'prompt) prompt) "Pattern: ") - data - :name str-command - :nomark (null crm) - :marked-candidates crm - :initial-input - (cond ((and file-comp-p - (not (string-match "/\\'" input))) - (concat (helm-mode--completion-in-region-initial-input - (helm-basename input)) - init-space-suffix)) - ((string-match "/\\'" input) nil) - ((or (null require-match) - (stringp require-match)) - (helm-mode--completion-in-region-initial-input input)) - (t (concat (helm-mode--completion-in-region-initial-input input) - init-space-suffix))) - :buffer buf-name - :fc-transformer - ;; Ensure sort fn is at the end. - (append '(helm-cr-default-transformer) - (and helm-completion-in-region-default-sort-fn - (list helm-completion-in-region-default-sort-fn))) - :match-dynamic (eq helm-completion-style 'emacs) - :fuzzy (eq helm-completion-style 'helm-fuzzy) - :exec-when-only-one t - :quit-when-no-cand - (lambda () - ;; Delay message to overwrite "Quit". - (run-with-timer - 0.01 nil - (lambda () - (message "[No matches]"))) - t) ; exit minibuffer immediately. - :must-match require-match)))) - (helm-completion-in-region--insert-result result start end base-size)) - (customize-set-variable 'helm-completion-style old--helm-completion-style) - (setq helm-completion--sorting-done nil) - (advice-remove 'lisp--local-variables - #'helm-mode--advice-lisp--local-variables))))) - -(defun helm-completion-in-region--insert-result (result start end base-size) - (cond ((stringp result) - (choose-completion-string - result (current-buffer) - (list (+ start base-size) end) - completion-list-insert-choice-function)) - ((consp result) ; crm. - (let ((beg (+ start base-size)) - (sep ",")) - ;; Try to find a default separator. - (save-excursion - (goto-char beg) - (when (looking-back crm-separator (1- (point))) - (setq sep (match-string 0)))) - (funcall completion-list-insert-choice-function - beg end (mapconcat 'identity result sep)))) - (t nil))) - -(defun helm-mode--in-file-completion-p () - (with-helm-current-buffer - (run-hook-with-args-until-success 'file-name-at-point-functions))) - -(when (boundp 'completion-in-region-function) - (defconst helm--old-completion-in-region-function completion-in-region-function)) - -(defun helm-mode--disable-ido-maybe (&optional from-hook) - (when (and (boundp 'ido-everywhere) ido-everywhere) - (remove-function read-file-name-function #'ido-read-file-name) - (remove-function read-buffer-function #'ido-read-buffer) - (setq ido-everywhere nil) - (if from-hook - (user-error "Unable to turn on Ido-everywhere while Helm-mode is enabled") - (user-error "Helm-mode enabled (Ido-everywhere is incompatible with Helm-mode, disabling it)")))) - -(defun helm-mode--ido-everywhere-hook () - ;; Called only when user calls directly ido-everywhere - ;; and helm-mode is enabled. - (when helm-mode - (helm-mode--disable-ido-maybe t))) - -;;;###autoload -(define-minor-mode helm-mode - "Toggle generic helm completion. - -All functions in Emacs that use `completing-read' -or `read-file-name' and friends will use helm interface -when this mode is turned on. - -However you can modify this behavior for functions of your choice -with `helm-completing-read-handlers-alist'. - -Also commands using `completion-in-region' will be helmized when -`helm-mode-handle-completion-in-region' is non nil, you can modify -this behavior with `helm-mode-no-completion-in-region-in-modes'. - -Called with a positive arg, turn on unconditionally, with a -negative arg turn off. -You can turn it on with `helm-mode'. - -Some crap emacs functions may not be supported, -e.g `ffap-alternate-file' and maybe others -You can add such functions to `helm-completing-read-handlers-alist' -with a nil value. - -About `ido-mode': -When you are using `helm-mode', DO NOT use `ido-mode', instead if you -want some commands use `ido', add these commands to -`helm-completing-read-handlers-alist' with `ido' as value. - -Note: This mode is incompatible with Emacs23." - :group 'helm-mode - :global t - :lighter helm-completion-mode-string - (cl-assert (boundp 'completing-read-function) nil - "`helm-mode' not available, upgrade to Emacs-24") - (if helm-mode - (if (fboundp 'add-function) - (progn - (add-function :override completing-read-function - #'helm--completing-read-default) - (add-function :override read-file-name-function - #'helm--generic-read-file-name) - (add-function :override read-buffer-function - #'helm--generic-read-buffer) - (when helm-mode-handle-completion-in-region - (add-function :override completion-in-region-function - #'helm--completion-in-region) - (helm-mode--setup-completion-styles)) - ;; If user have enabled ido-everywhere BEFORE enabling - ;; helm-mode disable it and warn user about its - ;; incompatibility with helm-mode (issue #2085). - (helm-mode--disable-ido-maybe) - ;; If ido-everywhere is not enabled yet anticipate and - ;; disable it if user attempt to enable it while helm-mode - ;; is running (issue #2085). - (add-hook 'ido-everywhere-hook #'helm-mode--ido-everywhere-hook)) - (setq completing-read-function 'helm--completing-read-default - read-file-name-function 'helm--generic-read-file-name - read-buffer-function 'helm--generic-read-buffer) - (when (and (boundp 'completion-in-region-function) - helm-mode-handle-completion-in-region) - (setq completion-in-region-function #'helm--completion-in-region) - (helm-mode--setup-completion-styles)) - (message helm-completion-mode-start-message)) - (if (fboundp 'remove-function) - (progn - (remove-function completing-read-function #'helm--completing-read-default) - (remove-function read-file-name-function #'helm--generic-read-file-name) - (remove-function read-buffer-function #'helm--generic-read-buffer) - (remove-function completion-in-region-function #'helm--completion-in-region) - (helm-mode--disable-completion-styles) - (remove-hook 'ido-everywhere-hook #'helm-mode--ido-everywhere-hook)) - (setq completing-read-function (and (fboundp 'completing-read-default) - 'completing-read-default) - read-file-name-function (and (fboundp 'read-file-name-default) - 'read-file-name-default) - read-buffer-function (and (fboundp 'read-buffer) 'read-buffer)) - (when (and (boundp 'completion-in-region-function) - (boundp 'helm--old-completion-in-region-function)) - (setq completion-in-region-function helm--old-completion-in-region-function) - (helm-mode--disable-completion-styles)) - (message helm-completion-mode-quit-message)))) - -(provide 'helm-mode) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-mode.el ends here diff --git a/elpa/helm-20191031.725/helm-net.el b/elpa/helm-20191031.725/helm-net.el deleted file mode 100644 index 59687009..00000000 --- a/elpa/helm-20191031.725/helm-net.el +++ /dev/null @@ -1,431 +0,0 @@ -;;; helm-net.el --- helm browse url and search web. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'cl-lib) -(require 'helm) -(require 'helm-help) -(require 'url) -(require 'xml) -(require 'browse-url) - - -(defgroup helm-net nil - "Net related applications and libraries for Helm." - :group 'helm) - -(defcustom helm-google-suggest-default-browser-function nil - "The browse url function you prefer to use with google suggest. -When nil, use the first browser function available -See `helm-browse-url-default-browser-alist'." - :group 'helm-net - :type 'symbol) - -(defcustom helm-home-url "https://www.google.com" - "Default url to use as home url." - :group 'helm-net - :type 'string) - -(defcustom helm-surfraw-default-browser-function nil - "The browse url function you prefer to use with surfraw. -When nil, fallback to `browse-url-browser-function'." - :group 'helm-net - :type 'symbol) - -(defcustom helm-google-suggest-url - "https://encrypted.google.com/complete/search?output=toolbar&q=%s" - "URL used for looking up Google suggestions. -This is a format string, don't forget the `%s'." - :type 'string - :group 'helm-net) - -(defcustom helm-google-suggest-search-url - "https://encrypted.google.com/search?ie=utf-8&oe=utf-8&q=%s" - "URL used for Google searching. -This is a format string, don't forget the `%s'." - :type 'string - :group 'helm-net) - -(defvaralias 'helm-google-suggest-use-curl-p 'helm-net-prefer-curl) -(make-obsolete-variable 'helm-google-suggest-use-curl-p 'helm-net-prefer-curl "1.7.7") - -(defcustom helm-net-prefer-curl nil - "When non--nil use CURL external program to fetch data. -Otherwise `url-retrieve-synchronously' is used." - :type 'boolean - :group 'helm-net) - -(defcustom helm-surfraw-duckduckgo-url - "https://duckduckgo.com/lite/?q=%s&kp=1" - "The duckduckgo url. -This is a format string, don't forget the `%s'. -If you have personal settings saved on duckduckgo you should have -a personal url, see your settings on duckduckgo." - :type 'string - :group 'helm-net) - -(defcustom helm-search-suggest-action-wikipedia-url - "https://en.wikipedia.org/wiki/Special:Search?search=%s" - "The Wikipedia search url. -This is a format string, don't forget the `%s'." - :type 'string - :group 'helm-net) - -(defcustom helm-search-suggest-action-youtube-url - "https://www.youtube.com/results?aq=f&search_query=%s" - "The Youtube search url. -This is a format string, don't forget the `%s'." - :type 'string - :group 'helm-net) - -(defcustom helm-search-suggest-action-imdb-url - "http://www.imdb.com/find?s=all&q=%s" - "The IMDb search url. -This is a format string, don't forget the `%s'." - :type 'string - :group 'helm-net) - -(defcustom helm-search-suggest-action-google-maps-url - "https://maps.google.com/maps?f=q&source=s_q&q=%s" - "The Google Maps search url. -This is a format string, don't forget the `%s'." - :type 'string - :group 'helm-net) - -(defcustom helm-search-suggest-action-google-news-url - "https://www.google.com/search?safe=off&prmd=nvlifd&source=lnms&tbs=nws:1&q=%s" - "The Google News search url. -This is a format string, don't forget the `%s'." - :type 'string - :group 'helm-net) - -(defcustom helm-google-suggest-actions - '(("Google Search" . helm-google-suggest-action) - ("Wikipedia" . (lambda (candidate) - (helm-search-suggest-perform-additional-action - helm-search-suggest-action-wikipedia-url - candidate))) - ("Youtube" . (lambda (candidate) - (helm-search-suggest-perform-additional-action - helm-search-suggest-action-youtube-url - candidate))) - ("IMDb" . (lambda (candidate) - (helm-search-suggest-perform-additional-action - helm-search-suggest-action-imdb-url - candidate))) - ("Google Maps" . (lambda (candidate) - (helm-search-suggest-perform-additional-action - helm-search-suggest-action-google-maps-url - candidate))) - ("Google News" . (lambda (candidate) - (helm-search-suggest-perform-additional-action - helm-search-suggest-action-google-news-url - candidate)))) - "List of actions for google suggest sources." - :group 'helm-net - :type '(alist :key-type string :value-type function)) - -(defcustom helm-browse-url-firefox-new-window "-new-tab" - "Allow choosing to browse url in new window or new tab. -Can be \"-new-tab\" (default) or \"-new-window\"." - :group 'helm-net - :type '(radio - (const :tag "New tab" "-new-tab") - (const :tag "New window" "-new-window"))) - -(defcustom helm-net-curl-switches '("-s" "-L") - "Arguments list passed to curl when using `helm-net-prefer-curl'." - :group 'helm-net - :type '(repeat string)) - -;;; Additional actions for search suggestions -;; -;; -;; Internal - -(defun helm-search-suggest-perform-additional-action (url query) - "Perform the search via URL using QUERY as input." - (browse-url (format url (url-hexify-string query)))) - -(defun helm-net--url-retrieve-sync (request parser) - (if helm-net-prefer-curl - (with-temp-buffer - (apply #'call-process "curl" - nil t nil request helm-net-curl-switches) - (funcall parser)) - (with-current-buffer (url-retrieve-synchronously request) - (funcall parser)))) - - -;;; Google Suggestions -;; -;; -(defun helm-google-suggest-parser () - (cl-loop - with result-alist = (xml-get-children - (car (xml-parse-region - (point-min) (point-max))) - 'CompleteSuggestion) - for i in result-alist collect - (cdr (cl-caadr (assq 'suggestion i))))) - -(defun helm-google-suggest-fetch (input) - "Fetch suggestions for INPUT from XML buffer." - (let ((request (format helm-google-suggest-url - (url-hexify-string input)))) - (helm-net--url-retrieve-sync - request #'helm-google-suggest-parser))) - -(defun helm-google-suggest-set-candidates (&optional request-prefix) - "Set candidates with result and number of google results found." - (let ((suggestions (helm-google-suggest-fetch - (or (and request-prefix - (concat request-prefix - " " helm-pattern)) - helm-pattern)))) - (if (member helm-pattern suggestions) - suggestions - ;; if there is no suggestion exactly matching the input then - ;; prepend a Search on Google item to the list - (append - suggestions - (list (cons (format "Search for '%s' on Google" helm-input) - helm-input)))))) - -(defun helm-ggs-set-number-result (num) - (if num - (progn - (and (numberp num) (setq num (number-to-string num))) - (cl-loop for i in (reverse (split-string num "" t)) - for count from 1 - append (list i) into C - when (= count 3) - append (list ",") into C - and do (setq count 0) - finally return - (replace-regexp-in-string - "^," "" (mapconcat 'identity (reverse C) "")))) - "?")) - -(defun helm-google-suggest-action (candidate) - "Default action to jump to a google suggested candidate." - (let ((arg (format helm-google-suggest-search-url - (url-hexify-string candidate)))) - (helm-aif helm-google-suggest-default-browser-function - (funcall it arg) - (helm-browse-url arg)))) - -(defvar helm-google-suggest-default-function - 'helm-google-suggest-set-candidates - "Default function to use in helm google suggest.") - -(defvar helm-source-google-suggest - (helm-build-sync-source "Google Suggest" - :candidates (lambda () - (funcall helm-google-suggest-default-function)) - :action 'helm-google-suggest-actions - :volatile t - :keymap helm-map - :requires-pattern 3)) - -(defun helm-google-suggest-emacs-lisp () - "Try to emacs lisp complete with google suggestions." - (helm-google-suggest-set-candidates "emacs lisp")) - - -;;; Web browser functions. -;; -;; -;; If default setting of `w3m-command' is not -;; what you want and you modify it, you will have to reeval -;; also `helm-browse-url-default-browser-alist'. - -(defvar helm-browse-url-chromium-program "chromium-browser") -(defvar helm-browse-url-uzbl-program "uzbl-browser") -(defvar helm-browse-url-conkeror-program "conkeror") -(defvar helm-browse-url-opera-program "opera") -(defvar helm-browse-url-default-browser-alist - `((,(or (and (boundp 'w3m-command) w3m-command) - "/usr/bin/w3m") . w3m-browse-url) - (,browse-url-firefox-program . browse-url-firefox) - (,helm-browse-url-chromium-program . helm-browse-url-chromium) - (,helm-browse-url-conkeror-program . helm-browse-url-conkeror) - (,helm-browse-url-opera-program . helm-browse-url-opera) - (,helm-browse-url-uzbl-program . helm-browse-url-uzbl) - (,browse-url-kde-program . browse-url-kde) - (,browse-url-gnome-moz-program . browse-url-gnome-moz) - (,browse-url-mozilla-program . browse-url-mozilla) - (,browse-url-galeon-program . browse-url-galeon) - (,browse-url-netscape-program . browse-url-netscape) - (,browse-url-mosaic-program . browse-url-mosaic) - (,browse-url-xterm-program . browse-url-text-xterm) - ("emacs" . eww-browse-url)) - "*Alist of \(executable . function\) to try to find a suitable url browser.") - -(cl-defun helm-generic-browser (url cmd-name &rest args) - "Browse URL with NAME browser." - (let ((proc (concat cmd-name " " url))) - (message "Starting %s..." cmd-name) - (apply 'start-process proc nil cmd-name - (append args (list url))) - (set-process-sentinel - (get-process proc) - (lambda (process event) - (when (string= event "finished\n") - (message "%s process %s" process event)))))) - -;;;###autoload -(defun helm-browse-url-firefox (url &optional _ignore) - "Same as `browse-url-firefox' but detach from emacs. - -So when you quit emacs you can keep your firefox session open -and not be prompted to kill firefox process. - -NOTE: Probably not supported on some systems (e.g Windows)." - (interactive (list (read-string "URL: " (browse-url-url-at-point)) - nil)) - (setq url (browse-url-encode-url url)) - (let ((process-environment (browse-url-process-environment))) - (call-process-shell-command - (format "(%s %s %s &)" - browse-url-firefox-program - helm-browse-url-firefox-new-window - (shell-quote-argument url))))) - -;;;###autoload -(defun helm-browse-url-opera (url &optional _ignore) - "Browse URL with opera browser and detach from emacs. - -So when you quit emacs you can keep your opera session open -and not be prompted to kill opera process. - -NOTE: Probably not supported on some systems (e.g Windows)." - (interactive (list (read-string "URL: " (browse-url-url-at-point)) - nil)) - (setq url (browse-url-encode-url url)) - (let ((process-environment (browse-url-process-environment))) - (call-process-shell-command - (format "(%s %s &)" - helm-browse-url-opera-program (shell-quote-argument url))))) - -;;;###autoload -(defun helm-browse-url-chromium (url &optional _ignore) - "Browse URL with google chrome browser." - (interactive "sURL: ") - (helm-generic-browser - url helm-browse-url-chromium-program)) - -;;;###autoload -(defun helm-browse-url-uzbl (url &optional _ignore) - "Browse URL with uzbl browser." - (interactive "sURL: ") - (helm-generic-browser url helm-browse-url-uzbl-program "-u")) - -;;;###autoload -(defun helm-browse-url-conkeror (url &optional _ignore) - "Browse URL with conkeror browser." - (interactive "sURL: ") - (helm-generic-browser url helm-browse-url-conkeror-program)) - -(defun helm-browse-url-default-browser (url &rest args) - "Find the first available browser and ask it to load URL." - (let ((default-browser-fn - (cl-loop for (exe . fn) in helm-browse-url-default-browser-alist - thereis (and exe (executable-find exe) (fboundp fn) fn)))) - (if default-browser-fn - (apply default-browser-fn url args) - (error "No usable browser found")))) - -(defun helm-browse-url (url &rest args) - "Default command to browse URL." - (if browse-url-browser-function - (browse-url url args) - (helm-browse-url-default-browser url args))) - - -;;; Surfraw -;; -;; Need external program surfraw. -;; - -;; Internal -(defvar helm-surfraw-engines-history nil) -(defvar helm-surfraw-input-history nil) -(defvar helm-surfraw--elvi-cache nil) - -(defun helm-build-elvi-list () - "Return list of all engines and descriptions handled by surfraw." - (or helm-surfraw--elvi-cache - (setq helm-surfraw--elvi-cache - (cdr (with-temp-buffer - (call-process "surfraw" nil t nil "-elvi") - (split-string (buffer-string) "\n")))))) - -;;;###autoload -(defun helm-surfraw (pattern engine) - "Preconfigured `helm' to search PATTERN with search ENGINE." - (interactive - (list - (let* ((default (if (use-region-p) - (buffer-substring-no-properties - (region-beginning) (region-end)) - (thing-at-point 'symbol))) - (prompt (if default - (format "SearchFor (default %s): " default) - "SearchFor: "))) - (read-string prompt nil 'helm-surfraw-input-history default)) - (helm-comp-read - "Engine: " - (helm-build-elvi-list) - :must-match t - :name "Surfraw Search Engines" - :del-input nil - :history helm-surfraw-engines-history))) - (let* ((engine-nodesc (car (split-string engine))) - (url (if (string= engine-nodesc "duckduckgo") - ;; "sr duckduckgo -p foo" is broken, workaround. - (format helm-surfraw-duckduckgo-url - (url-hexify-string pattern)) - (with-temp-buffer - (apply 'call-process "surfraw" nil t nil - (append (list engine-nodesc "-p") (split-string pattern))) - (replace-regexp-in-string - "\n" "" (buffer-string))))) - (browse-url-browser-function (or helm-surfraw-default-browser-function - browse-url-browser-function))) - (if (string= engine-nodesc "W") - (helm-browse-url helm-home-url) - (helm-browse-url url) - (setq helm-surfraw-engines-history - (cons engine (delete engine helm-surfraw-engines-history)))))) - -;;;###autoload -(defun helm-google-suggest () - "Preconfigured `helm' for google search with google suggest." - (interactive) - (helm-other-buffer 'helm-source-google-suggest "*helm google*")) - -(provide 'helm-net) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-net.el ends here diff --git a/elpa/helm-20191031.725/helm-occur.el b/elpa/helm-20191031.725/helm-occur.el deleted file mode 100644 index 72fc70ad..00000000 --- a/elpa/helm-20191031.725/helm-occur.el +++ /dev/null @@ -1,701 +0,0 @@ -;;; helm-occur.el --- Incremental Occur for Helm. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - - -;;; Code: - -(require 'cl-lib) -(require 'helm) -(require 'helm-help) -(require 'helm-utils) - -;;; Internals -;; -(defvar helm-source-occur nil) -(defvar helm-source-moccur nil - "This is just a flag to add to `helm-sources-using-default-as-input'. -Don't set it to any value, it will have no effect.") -(defvar helm-occur--buffer-list nil) -(defvar helm-occur--buffer-tick nil) -(defvar helm-occur-history nil) -(defvar helm-occur--search-buffer-regexp "\\`\\([0-9]*\\)\\s-\\{1\\}\\(.*\\)\\'" - "The regexp matching candidates in helm-occur candidate buffer.") -(defvar helm-occur-mode--last-pattern nil) - - -(defvar helm-occur-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "C-c o") 'helm-occur-run-goto-line-ow) - (define-key map (kbd "C-c C-o") 'helm-occur-run-goto-line-of) - (define-key map (kbd "C-x C-s") 'helm-occur-run-save-buffer) - map) - "Keymap used in occur source.") - -(defgroup helm-occur nil - "Regexp related Applications and libraries for Helm." - :group 'helm) - -(defcustom helm-occur-actions - '(("Go to Line" . helm-occur-goto-line) - ("Goto line other window (C-u vertically)" . helm-occur-goto-line-ow) - ("Goto line new frame" . helm-occur-goto-line-of) - ("Save buffer" . helm-occur-save-results) - ) - "Actions for helm-occur." - :group 'helm-occur - :type '(alist :key-type string :value-type function)) - -(defcustom helm-occur-use-ioccur-style-keys nil - "Similar to `helm-grep-use-ioccur-style-keys' but for multi occur. - -Note that if you define this variable with `setq' your change will -have no effect, use customize instead." - :group 'helm-occur - :type 'boolean - :set (lambda (var val) - (set var val) - (if val - (progn - (define-key helm-occur-map (kbd "") 'helm-occur-right) - (define-key helm-occur-map (kbd "") 'helm-occur-run-default-action)) - (define-key helm-occur-map (kbd "") nil) - (define-key helm-occur-map (kbd "") nil)))) - -(defcustom helm-occur-always-search-in-current nil - "Helm multi occur always search in current buffer when non--nil." - :group 'helm-occur - :type 'boolean) - -(defcustom helm-occur-truncate-lines t - "Truncate lines in occur buffer when non nil." - :group 'helm-occur - :type 'boolean) - -(defcustom helm-occur-auto-update-on-resume nil - "Allow auto updating helm-occur buffer when outdated. -noask => Always update without asking -nil => Don't update but signal buffer needs update -never => Never update and do not signal buffer needs update -Any other non--nil value update after confirmation." - :group 'helm-regexp - :type '(radio :tag "Allow auto updating helm-occur buffer when outdated." - (const :tag "Always update without asking" noask) - (const :tag "Never update and do not signal buffer needs update" never) - (const :tag "Don't update but signal buffer needs update" nil) - (const :tag "Update after confirmation" t))) - -(defcustom helm-occur-candidate-number-limit 99999 - "Value of `helm-candidate-number-limit' for helm-occur." - :group 'helm-occur - :type 'integer) - -(defcustom helm-occur-buffer-substring-fn-for-modes - '((mu4e-headers-mode . buffer-substring)) - "Function to use to display buffer contents for major-mode. - -Can be one of `buffer-substring' or `buffer-substring-no-properties'. - -Note that when using `buffer-substring' initialization will be slower." - :group 'helm-regexp - :type '(alist :key-type (symbol :tag "Mode") - :value-type (radio (const :tag "With text properties" buffer-substring) - (const :tag "Without text properties" buffer-substring-no-properties)))) - - -(defface helm-moccur-buffer - '((t (:foreground "DarkTurquoise" :underline t))) - "Face used to highlight occur buffer names." - :group 'helm-occur) - -(defface helm-resume-need-update - '((t (:background "red"))) - "Face used to flash occur buffer when it needs update." - :group 'helm-occur) - - -;;;###autoload -(defun helm-occur () - "Preconfigured helm for searching lines matching pattern in `current-buffer'. - -When `helm-source-occur' is member of -`helm-sources-using-default-as-input' which is the default, -symbol at point is searched at startup. - -When a region is marked search only in this region by narrowing. - -To search in multiples buffers start from one of the commands listing -buffers (i.e. a helm command using `helm-source-buffers-list' like -`helm-mini') and use the multi occur buffers action. - -This is the helm implementation that collect lines matching pattern -like vanilla emacs `occur' but have nothing to do with it, the search -engine beeing completely different and also much faster." - (interactive) - (setq helm-source-occur - (car (helm-occur-build-sources (list (current-buffer)) "Helm occur"))) - (helm-set-local-variable 'helm-occur--buffer-list (list (current-buffer)) - 'helm-occur--buffer-tick - (list (buffer-chars-modified-tick (current-buffer)))) - (save-restriction - (let (def pos) - (when (use-region-p) - ;; When user mark defun with `mark-defun' with intention of - ;; using helm-occur on this region, it is relevant to use the - ;; thing-at-point located at previous position which have been - ;; pushed to `mark-ring'. - (setq def (save-excursion - (goto-char (setq pos (car mark-ring))) - (helm-aif (thing-at-point 'symbol) (regexp-quote it)))) - (narrow-to-region (region-beginning) (region-end))) - (unwind-protect - (helm :sources 'helm-source-occur - :buffer "*helm occur*" - :history 'helm-occur-history - :default (or def (helm-aif (thing-at-point 'symbol) - (regexp-quote it))) - :preselect (and (memq 'helm-source-occur - helm-sources-using-default-as-input) - (format "^%d:" (line-number-at-pos - (or pos (point))))) - :truncate-lines helm-occur-truncate-lines) - (deactivate-mark t))))) - -(defun helm-occur-transformer (candidates source) - "Returns CANDIDATES prefixed with line number." - (cl-loop with buf = (helm-attr 'buffer-name source) - for c in candidates collect - (when (string-match helm-occur--search-buffer-regexp c) - (let ((linum (match-string 1 c)) - (disp (match-string 2 c))) - (cons (format "%s:%s" - (propertize - linum 'face 'helm-grep-lineno - 'help-echo (buffer-file-name - (get-buffer buf))) - disp) - (string-to-number linum)))))) - -(defclass helm-moccur-class (helm-source-in-buffer) - ((buffer-name :initarg :buffer-name - :initform nil) - (moccur-buffers :initarg :moccur-buffers - :initform nil))) - -(defun helm-occur-build-sources (buffers &optional source-name) - "Build sources for helm-occur for each buffer in BUFFERS list." - (cl-loop for buf in buffers - collect - (helm-make-source (or source-name - (format "HO [%s]" - (buffer-name buf))) - 'helm-moccur-class - :buffer-name (buffer-name buf) - :match-part - (lambda (candidate) - ;; The regexp should match what is in candidate buffer, - ;; not what is displayed in helm-buffer e.g. "12 foo" - ;; and not "12:foo". - (when (string-match helm-occur--search-buffer-regexp - candidate) - (match-string 2 candidate))) - :search (lambda (pattern) - (when (string-match "\\`\\^\\([^ ]*\\)" pattern) - (setq pattern (concat "^[0-9]* \\{1\\}" (match-string 1 pattern)))) - (condition-case _err - (re-search-forward pattern nil t) - (invalid-regexp nil))) - :init `(lambda () - (with-current-buffer ,buf - (let* ((bsfn (or (cdr (assq - major-mode - helm-occur-buffer-substring-fn-for-modes)) - #'buffer-substring-no-properties)) - (contents (funcall bsfn (point-min) (point-max)))) - (helm-attrset 'get-line bsfn) - (with-current-buffer (helm-candidate-buffer 'local) - (insert contents) - (goto-char (point-min)) - (let ((linum 1)) - (insert (format "%s " linum)) - (while (re-search-forward "\n" nil t) - (cl-incf linum) - (insert (format "%s " linum)))))))) - :filtered-candidate-transformer 'helm-occur-transformer - :help-message 'helm-moccur-help-message - :nomark t - :migemo t - ;; Needed for resume. - :history 'helm-occur-history - :candidate-number-limit helm-occur-candidate-number-limit - :action 'helm-occur-actions - :requires-pattern 2 - :follow 1 - :group 'helm-occur - :keymap helm-occur-map - :resume 'helm-occur-resume-fn - :moccur-buffers buffers))) - -(defun helm-multi-occur-1 (buffers &optional input) - "Runs helm-occur on a list of buffers. -Each buffer's result is displayed in a separated source." - (let* ((curbuf (current-buffer)) - (bufs (if helm-occur-always-search-in-current - (cons curbuf (remove curbuf buffers)) - buffers)) - (sources (helm-occur-build-sources bufs)) - (helm--maybe-use-default-as-input - (not (null (memq 'helm-source-moccur - helm-sources-using-default-as-input))))) - (helm-set-local-variable 'helm-occur--buffer-list bufs - 'helm-occur--buffer-tick - (cl-loop for b in bufs collect - (buffer-chars-modified-tick - (get-buffer b)))) - (helm :sources sources - :buffer "*helm moccur*" - :history 'helm-occur-history - :default (helm-aif (thing-at-point 'symbol) (regexp-quote it)) - :input input - :truncate-lines helm-occur-truncate-lines))) - -;;; Actions -;; -(cl-defun helm-occur-action (lineno - &optional (method (quote buffer))) - "Jump to line number LINENO with METHOD. -arg METHOD can be one of buffer, buffer-other-window, buffer-other-frame." - (require 'helm-grep) - (let ((buf (if (eq major-mode 'helm-occur-mode) - (get-text-property (point) 'buffer-name) - (helm-attr 'buffer-name))) - (split-pat (helm-mm-split-pattern helm-input))) - (cl-case method - (buffer (switch-to-buffer buf)) - (buffer-other-window (helm-window-show-buffers (list buf) t)) - (buffer-other-frame (switch-to-buffer-other-frame buf))) - (with-current-buffer buf - (helm-goto-line lineno) - ;; Move point to the nearest matching regexp from bol. - (cl-loop for reg in split-pat - when (save-excursion - (condition-case _err - (if helm-migemo-mode - (helm-mm-migemo-forward reg (point-at-eol) t) - (re-search-forward reg (point-at-eol) t)) - (invalid-regexp nil))) - collect (match-beginning 0) into pos-ls - finally (when pos-ls (goto-char (apply #'min pos-ls))))))) - -(defun helm-occur-goto-line (candidate) - "From multi occur, switch to buffer and CANDIDATE line." - (helm-occur-action - candidate 'buffer)) - -(defun helm-occur-goto-line-ow (candidate) - "Go to CANDIDATE line in other window. -Same as `helm-occur-goto-line' but go in other window." - (helm-occur-action - candidate 'buffer-other-window)) - -(defun helm-occur-goto-line-of (candidate) - "Go to CANDIDATE line in new frame. -Same as `helm-occur-goto-line' but go in new frame." - (helm-occur-action - candidate 'buffer-other-frame)) - -(defun helm-occur-run-goto-line-ow () - "Run goto line other window action from `helm-occur'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-occur-goto-line-ow))) -(put 'helm-occur-run-goto-line-ow 'helm-only t) - -(defun helm-occur-run-goto-line-of () - "Run goto line new frame action from `helm-occur'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-occur-goto-line-of))) -(put 'helm-occur-run-goto-line-of 'helm-only t) - -(defun helm-occur-run-default-action () - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-occur-goto-line))) -(put 'helm-occur-run-default-action 'helm-only t) - -(defun helm-occur-run-save-buffer () - "Run moccur save results action from `helm-moccur'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-occur-save-results))) -(put 'helm-moccur-run-save-buffer 'helm-only t) - -(defun helm-occur-right () - "helm-occur action for right arrow. -This is used when `helm-occur-use-ioccur-style-keys' is enabled. -If follow is enabled (default) go to next source, otherwise execute -persistent action." - (interactive) - (if (helm-aand (helm-attr 'follow) (> it 0)) - (helm-next-source) - (helm-execute-persistent-action))) -(put 'helm-occur-right 'helm-only t) - - -;;; helm-occur-mode -;; -;; -(defvar helm-occur-mode-map - (let ((map (make-sparse-keymap))) - (define-key map (kbd "RET") 'helm-occur-mode-goto-line) - (define-key map (kbd "C-o") 'helm-occur-mode-goto-line-ow) - (define-key map (kbd "") 'helm-occur-mode-goto-line-ow-forward) - (define-key map (kbd "") 'helm-occur-mode-goto-line-ow-backward) - (define-key map (kbd "") 'helm-gm-next-file) - (define-key map (kbd "") 'helm-gm-precedent-file) - (define-key map (kbd "M-n") 'helm-occur-mode-goto-line-ow-forward) - (define-key map (kbd "M-p") 'helm-occur-mode-goto-line-ow-backward) - (define-key map (kbd "M-N") 'helm-gm-next-file) - (define-key map (kbd "M-P") 'helm-gm-precedent-file) - (define-key map (kbd "C-c b") 'helm-occur-mode-resume-session) - map)) - -(defun helm-occur-mode-goto-line () - (interactive) - (helm-aif (get-text-property (point) 'helm-realvalue) - (progn (helm-occur-goto-line it) (helm-match-line-cleanup-pulse)))) - -(defun helm-occur-mode-goto-line-ow () - (interactive) - (helm-aif (get-text-property (point) 'helm-realvalue) - (progn (helm-occur-goto-line-ow it) (helm-match-line-cleanup-pulse)))) - -(defun helm-occur-mode-goto-line-ow-forward-1 (arg) - (condition-case nil - (progn - (when (or (eq last-command 'helm-occur-mode-goto-line-ow-forward) - (eq last-command 'helm-occur-mode-goto-line-ow-backward)) - (forward-line arg)) - (save-selected-window - (helm-occur-mode-goto-line-ow) - (recenter))) - (error nil))) - -(defun helm-occur-mode-goto-line-ow-forward (arg) - (interactive "p") - (helm-occur-mode-goto-line-ow-forward-1 arg)) - -(defun helm-occur-mode-goto-line-ow-backward (arg) - (interactive "p") - (helm-occur-mode-goto-line-ow-forward-1 (- arg))) - -(defun helm-occur-save-results (_candidate) - "Save helm moccur results in a `helm-moccur-mode' buffer." - (let ((buf "*hmoccur*") - new-buf) - (when (get-buffer buf) - (setq new-buf (helm-read-string "OccurBufferName: " buf)) - (cl-loop for b in (helm-buffer-list) - when (and (string= new-buf b) - (not (y-or-n-p - (format "Buffer `%s' already exists overwrite? " - new-buf)))) - do (setq new-buf (helm-read-string - "OccurBufferName: " "*hmoccur "))) - (setq buf new-buf)) - (with-current-buffer (get-buffer-create buf) - (kill-all-local-variables) - (setq buffer-read-only t) - (buffer-disable-undo) - (let ((inhibit-read-only t) - (map (make-sparse-keymap)) - buf-name) - (erase-buffer) - (insert "-*- mode: helm-occur -*-\n\n" - (format "Occur Results for `%s':\n\n" helm-input)) - (save-excursion - (insert (with-current-buffer helm-buffer - (goto-char (point-min)) - (forward-line 1) - (buffer-substring (point) (point-max))))) - (save-excursion - (forward-line -2) - (while (not (eobp)) - (if (helm-pos-header-line-p) - (let ((beg (point-at-bol)) - (end (point-at-eol))) - (set-text-properties beg (1+ end) nil) - (delete-region (1- beg) end)) - (helm-aif (setq buf-name (assoc-default - 'buffer-name - (get-text-property (point) 'helm-cur-source))) - (progn - (insert (propertize (concat it ":") - 'face 'helm-moccur-buffer - 'helm-realvalue (get-text-property (point) 'helm-realvalue))) - (add-text-properties - (point-at-bol) (point-at-eol) - `(buffer-name ,buf-name)) - (add-text-properties - (point-at-bol) (point-at-eol) - `(keymap ,map - help-echo ,(concat - (buffer-file-name - (get-buffer buf-name)) - "\nmouse-1: set point\nmouse-2: jump to selection") - mouse-face highlight - invisible nil)) - (define-key map [mouse-1] 'mouse-set-point) - (define-key map [mouse-2] 'helm-occur-mode-mouse-goto-line) - (define-key map [mouse-3] 'ignore)))) - (forward-line 1)))) - (buffer-enable-undo) - (helm-occur-mode)) - (pop-to-buffer buf) - (message "Helm occur Results saved in `%s' buffer" buf))) - -(defun helm-occur-mode-mouse-goto-line (event) - (interactive "e") - (let* ((window (posn-window (event-end event))) - (pos (posn-point (event-end event)))) - (with-selected-window window - (when (eq major-mode 'helm-occur-mode) - (goto-char pos) - (helm-occur-mode-goto-line))))) -(put 'helm-moccur-mode-mouse-goto-line 'helm-only t) - -(defun helm-occur-mode-resume-session () - (interactive) - (cl-assert (eq major-mode 'helm-occur-mode) nil "Helm command called in wrong context") - (helm-multi-occur-1 helm-occur--buffer-list helm-occur-mode--last-pattern)) - -(defun helm-occur-buffer-substring-with-linums () - "Returns current-buffer contents as a string with all lines -numbered. The property 'buffer-name is added to the whole string." - (let ((bufstr (buffer-substring-no-properties (point-min) (point-max))) - (bufname (buffer-name))) - (with-temp-buffer - (save-excursion - (insert bufstr)) - (let ((linum 1)) - (insert (format "%s " linum)) - (while (re-search-forward "\n" nil t) - (cl-incf linum) - (insert (format "%s " linum))) - (add-text-properties (point-min) (point-max) `(buffer-name ,bufname))) - (buffer-string)))) - -(defun helm-occur-mode--revert-buffer-function (&optional _ignore-auto _noconfirm) - "The `revert-buffer-function' for `helm-occur-mode'." - (goto-char (point-min)) - (let (pattern) - (when (re-search-forward "^Occur Results for `\\(.*\\)'" nil t) - (setq pattern (match-string 1)) - (forward-line 0) - (when (re-search-forward "^$" nil t) - (forward-line 1)) - (let ((inhibit-read-only t) - (buffer (current-buffer)) - (buflst helm-occur--buffer-list)) - (delete-region (point) (point-max)) - (message "Reverting buffer...") - (save-excursion - (with-temp-buffer - (insert - "\n" - (cl-loop for buf in buflst - for bufstr = (or (and (buffer-live-p (get-buffer buf)) - (with-current-buffer buf - (helm-occur-buffer-substring-with-linums))) - "") - concat bufstr) - "\n") - (goto-char (point-min)) - (cl-loop with linum - with mpart - ;; Bind helm-pattern used by `helm-grep-split-line'. - with helm-pattern = pattern - while (helm-mm-search pattern) ; point is at eol. - ;; Calculate line number (linum) and extract real - ;; part of line (mpart). - do (when (save-excursion - ;; `helm-mm-search' puts point at eol. - (forward-line 0) - (re-search-forward "^\\([0-9]*\\)\\s-\\{1\\}\\(.*\\)$" - (point-at-eol) t)) - (setq linum (string-to-number (match-string 1)) - mpart (match-string 2))) - ;; Match part after line number. - when (and mpart (string-match pattern mpart)) - for line = (format "%s:%d:%s" - (get-text-property (point) 'buffer-name) - linum - mpart) - when line - do (with-current-buffer buffer - (insert - (propertize - (car (helm-occur-filter-one-by-one line)) - 'helm-realvalue linum) - "\n")))) - (when (fboundp 'wgrep-cleanup-overlays) - (wgrep-cleanup-overlays (point-min) (point-max))) - (message "Reverting buffer done")))))) - -(defun helm-occur-filter-one-by-one (candidate) - "`filter-one-by-one' function for `helm-source-moccur'." - (require 'helm-grep) - (let* ((split (helm-grep-split-line candidate)) - (buf (car split)) - (lineno (nth 1 split)) - (str (nth 2 split))) - (cons (concat (propertize - buf - 'face 'helm-moccur-buffer - 'help-echo (buffer-file-name - (get-buffer buf)) - 'buffer-name buf) - ":" - (propertize lineno 'face 'helm-grep-lineno) - ":" - (helm-grep-highlight-match str t)) - candidate))) - -;;;###autoload -(define-derived-mode helm-occur-mode - special-mode "helm-moccur" - "Major mode to provide actions in helm moccur saved buffer. - -Special commands: -\\{helm-occur-mode-map}" - (set (make-local-variable 'helm-occur--buffer-list) - (with-helm-buffer helm-occur--buffer-list)) - (set (make-local-variable 'revert-buffer-function) - #'helm-occur-mode--revert-buffer-function) - (set (make-local-variable 'helm-occur-mode--last-pattern) - helm-input)) -(put 'helm-moccur-mode 'helm-only t) - - -;;; Resume -;; -(defun helm-occur-resume-fn () - (with-helm-buffer - (let (new-tick-ls buffer-is-modified) - (set (make-local-variable 'helm-occur--buffer-list) - (cl-loop for b in helm-occur--buffer-list - when (buffer-live-p (get-buffer b)) - collect b)) - (setq buffer-is-modified (/= (length helm-occur--buffer-list) - (length (helm-attr 'moccur-buffers)))) - (helm-attrset 'moccur-buffers helm-occur--buffer-list) - (setq new-tick-ls (cl-loop for b in helm-occur--buffer-list - collect (buffer-chars-modified-tick - (get-buffer b)))) - (when buffer-is-modified - (setq helm-occur--buffer-tick new-tick-ls)) - (cl-assert (> (length helm-occur--buffer-list) 0) nil - "helm-resume error: helm-(m)occur buffer list is empty") - (unless (eq helm-occur-auto-update-on-resume 'never) - (when (or buffer-is-modified - (cl-loop for b in helm-occur--buffer-list - for new-tick = (buffer-chars-modified-tick - (get-buffer b)) - for tick in helm-occur--buffer-tick - thereis (/= tick new-tick))) - (helm-aif helm-occur-auto-update-on-resume - (when (or (eq it 'noask) - (y-or-n-p "Helm (m)occur Buffer outdated, update? ")) - (run-with-idle-timer - 0.1 nil (lambda () - (with-helm-buffer - (helm-force-update) - (message "Helm (m)occur Buffer have been udated") - (sit-for 1) (message nil)))) - (unless buffer-is-modified (setq helm-occur--buffer-tick - new-tick-ls))) - (run-with-idle-timer - 0.1 nil - (lambda () - (with-helm-buffer - (let ((ov (make-overlay (save-excursion - (goto-char (point-min)) - (forward-line 1) - (point)) - (point-max)))) - (overlay-put ov 'face 'helm-resume-need-update) - (sit-for 0.3) (delete-overlay ov) - (message "[Helm occur Buffer outdated (C-c C-u to update)]"))))) - (unless buffer-is-modified - (with-helm-after-update-hook - (setq helm-occur--buffer-tick new-tick-ls) - (message "Helm (m)occur Buffer have been udated"))))))))) - -;;; Helm occur from isearch -;; -;;;###autoload -(defun helm-occur-from-isearch () - "Invoke `helm-occur' from isearch. - -To use this bind it to a key in `isearch-mode-map'." - (interactive) - (let ((input (if isearch-regexp - isearch-string - (regexp-quote isearch-string))) - (bufs (list (current-buffer)))) - (isearch-exit) - (helm-multi-occur-1 bufs input))) - -;;;###autoload -(defun helm-multi-occur-from-isearch () - "Invoke `helm-multi-occur' from isearch. - -With a prefix arg, reverse the behavior of -`helm-moccur-always-search-in-current'. -The prefix arg can be set before calling -`helm-multi-occur-from-isearch' or during the buffer selection. - -To use this bind it to a key in `isearch-mode-map'." - (interactive) - (let (buf-list - helm-moccur-always-search-in-current - (input (if isearch-regexp - isearch-string - (regexp-quote isearch-string)))) - (isearch-exit) - (setq buf-list (mapcar 'get-buffer - (helm-comp-read "Buffers: " - (helm-buffer-list) - :name "Occur in buffer(s)" - :marked-candidates t))) - (setq helm-moccur-always-search-in-current - (if (or current-prefix-arg - helm-current-prefix-arg) - (not helm-moccur-always-search-in-current) - helm-moccur-always-search-in-current)) - (helm-multi-occur-1 buf-list input))) - -(provide 'helm-occur) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-occur.el ends here diff --git a/elpa/helm-20191031.725/helm-pkg.el b/elpa/helm-20191031.725/helm-pkg.el deleted file mode 100644 index fa05c8c3..00000000 --- a/elpa/helm-20191031.725/helm-pkg.el +++ /dev/null @@ -1,9 +0,0 @@ -(define-package "helm" "20191031.725" "Helm is an Emacs incremental and narrowing framework" - '((emacs "24.4") - (async "1.9.3") - (popup "0.5.3") - (helm-core "3.0")) - :url "https://emacs-helm.github.io/helm/") -;; Local Variables: -;; no-byte-compile: t -;; End: diff --git a/elpa/helm-20191031.725/helm-regexp.el b/elpa/helm-20191031.725/helm-regexp.el deleted file mode 100644 index 8c2e2b3e..00000000 --- a/elpa/helm-20191031.725/helm-regexp.el +++ /dev/null @@ -1,138 +0,0 @@ -;;; helm-regexp.el --- In buffer regexp searching and replacement for helm. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'cl-lib) -(require 'helm) -(require 'helm-help) -(require 'helm-utils) - -(declare-function helm-mm-split-pattern "helm-multi-match") - - -(defgroup helm-regexp nil - "Regexp related Applications and libraries for Helm." - :group 'helm) - - - -;; History vars -(defvar helm-build-regexp-history nil) - -(defun helm-query-replace-regexp (_candidate) - "Query replace regexp from `helm-regexp'. -With a prefix arg replace only matches surrounded by word boundaries, -i.e Don't replace inside a word, regexp is surrounded with \\bregexp\\b." - (let ((regexp helm-input)) - (apply 'query-replace-regexp - (helm-query-replace-args regexp)))) - -(defun helm-kill-regexp-as-sexp (_candidate) - "Kill regexp in a format usable in lisp code." - (helm-regexp-kill-new - (prin1-to-string helm-input))) - -(defun helm-kill-regexp (_candidate) - "Kill regexp as it is in `helm-pattern'." - (helm-regexp-kill-new helm-input)) - -(defun helm-query-replace-args (regexp) - "create arguments of `query-replace-regexp' action in `helm-regexp'." - (let ((region-only (helm-region-active-p))) - (list - regexp - (query-replace-read-to regexp - (format "Query replace %sregexp %s" - (if helm-current-prefix-arg "word " "") - (if region-only "in region " "")) - t) - helm-current-prefix-arg - (when region-only (region-beginning)) - (when region-only (region-end))))) - -(defvar helm-source-regexp - (helm-build-in-buffer-source "Regexp Builder" - :init (lambda () - (helm-init-candidates-in-buffer - 'global (with-temp-buffer - (insert-buffer-substring helm-current-buffer) - (buffer-string)))) - :get-line #'helm-regexp-get-line - :persistent-action #'helm-regexp-persistent-action - :persistent-help "Show this line" - :multiline t - :multimatch nil - :requires-pattern 2 - :group 'helm-regexp - :mode-line "Press TAB to select action." - :action '(("Kill Regexp as sexp" . helm-kill-regexp-as-sexp) - ("Query Replace Regexp (C-u Not inside word.)" - . helm-query-replace-regexp) - ("Kill Regexp" . helm-kill-regexp)))) - -(defun helm-regexp-get-line (s e) - (let ((matches (match-data)) - (line (buffer-substring s e))) - (propertize - (cl-loop with ln = (format "%5d: %s" (1- (line-number-at-pos s)) line) - for i from 0 to (1- (/ (length matches) 2)) - if (match-string i) - concat (format "\n%s%s'%s'" - (make-string 10 ? ) (format "Group %d: " i) it) - into ln1 - finally return (concat ln ln1)) - 'helm-realvalue s))) - -(defun helm-regexp-persistent-action (pt) - (helm-goto-char pt) - (helm-highlight-current-line)) - -(defun helm-regexp-kill-new (input) - (kill-new (substring-no-properties input)) - (message "Killed: %s" input)) - - -;;; Predefined commands -;; -;; - -;;;###autoload -(defun helm-regexp () - "Preconfigured helm to build regexps. -`query-replace-regexp' can be run from there against found regexp." - (interactive) - (save-restriction - (when (and (helm-region-active-p) - ;; Don't narrow to region if buffer is already narrowed. - (not (helm-current-buffer-narrowed-p (current-buffer)))) - (narrow-to-region (region-beginning) (region-end))) - (helm :sources helm-source-regexp - :buffer "*helm regexp*" - :prompt "Regexp: " - :history 'helm-build-regexp-history))) - - -(provide 'helm-regexp) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-regexp.el ends here diff --git a/elpa/helm-20191031.725/helm-ring.el b/elpa/helm-20191031.725/helm-ring.el deleted file mode 100644 index f4504d53..00000000 --- a/elpa/helm-20191031.725/helm-ring.el +++ /dev/null @@ -1,591 +0,0 @@ -;;; helm-ring.el --- kill-ring, mark-ring, and register browsers for helm. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'cl-lib) -(require 'helm) -(require 'helm-utils) -(require 'helm-help) -(require 'helm-elisp) - -(declare-function undo-tree-restore-state-from-register "ext:undo-tree.el" (register)) - - -(defgroup helm-ring nil - "Ring related Applications and libraries for Helm." - :group 'helm) - -(defcustom helm-kill-ring-threshold 3 - "Minimum length of a candidate to be listed by `helm-source-kill-ring'." - :type 'integer - :group 'helm-ring) - -(defcustom helm-kill-ring-max-offset 400 - "Max number of chars displayed per candidate in kill-ring browser. -When `t', don't truncate candidate, show all. -By default it is approximatively the number of bits contained in five lines -of 80 chars each i.e 80*5. -Note that if you set this to nil multiline will be disabled, i.e you -will not have anymore separators between candidates." - :type '(choice (const :tag "Disabled" t) - (integer :tag "Max candidate offset")) - :group 'helm-ring) - -(defcustom helm-kill-ring-actions - '(("Yank marked" . helm-kill-ring-action-yank) - ("Delete marked" . helm-kill-ring-action-delete)) - "List of actions for kill ring source." - :group 'helm-ring - :type '(alist :key-type string :value-type function)) - -(defcustom helm-kill-ring-separator "\n" - "The separator used to separate marked candidates when yanking." - :group 'helm-ring - :type 'string) - -(defcustom helm-register-max-offset 160 - "Max size of string register entries before truncating." - :group 'helm-ring - :type 'integer) - -;;; Kill ring -;; -;; -(defvar helm-kill-ring-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "M-y") 'helm-next-line) - (define-key map (kbd "M-u") 'helm-previous-line) - (define-key map (kbd "M-D") 'helm-kill-ring-delete) - (define-key map (kbd "C-]") 'helm-kill-ring-toggle-truncated) - (define-key map (kbd "C-c C-k") 'helm-kill-ring-kill-selection) - (define-key map (kbd "C-c d") 'helm-kill-ring-run-persistent-delete) - map) - "Keymap for `helm-show-kill-ring'.") - -(defvar helm-source-kill-ring - (helm-build-sync-source "Kill Ring" - :init (lambda () - (helm-attrset 'last-command last-command) - (helm-attrset 'multiline helm-kill-ring-max-offset)) - :candidates #'helm-kill-ring-candidates - :filtered-candidate-transformer #'helm-kill-ring-transformer - :action 'helm-kill-ring-actions - :persistent-action 'ignore - :help-message 'helm-kill-ring-help-message - :persistent-help "DoNothing" - :keymap helm-kill-ring-map - :migemo t - :multiline 'helm-kill-ring-max-offset - :group 'helm-ring) - "Source for browse and insert contents of kill-ring.") - -(defun helm-kill-ring-candidates () - (cl-loop with cands = (helm-fast-remove-dups kill-ring :test 'equal) - for kill in (if (eq (helm-attr 'last-command) 'yank) - (cdr cands) - cands) - unless (or (< (length kill) helm-kill-ring-threshold) - (string-match "\\`[\n[:blank:]]+\\'" kill)) - collect kill)) - -(defun helm-kill-ring-transformer (candidates _source) - "Ensure CANDIDATES are not read-only." - (cl-loop for i in candidates - when (get-text-property 0 'read-only i) - do (set-text-properties 0 (length i) '(read-only nil) i) - collect i)) - -(defvar helm-kill-ring--truncated-flag nil) -(defun helm-kill-ring-toggle-truncated () - "Toggle truncated view of candidates in helm kill-ring browser." - (interactive) - (with-helm-alive-p - (setq helm-kill-ring--truncated-flag (not helm-kill-ring--truncated-flag)) - (let* ((cur-cand (helm-get-selection)) - (presel-fn (lambda () - (helm-kill-ring--preselect-fn cur-cand)))) - (helm-attrset 'multiline - (if helm-kill-ring--truncated-flag - 15000000 - helm-kill-ring-max-offset)) - (helm-update presel-fn)))) -(put 'helm-kill-ring-toggle-truncated 'helm-only t) - -(defun helm-kill-ring-kill-selection () - "Store the real value of candidate in kill-ring. -Same as `helm-kill-selection-and-quit' called with a prefix arg." - (interactive) - (helm-kill-selection-and-quit t)) -(put 'helm-kill-ring-kill-selection 'helm-only t) - -(defun helm-kill-ring--preselect-fn (candidate) - "Internal, used to preselect CANDIDATE when toggling truncated view." - ;; Preselection by regexp may not work if candidate is huge, so walk - ;; the helm buffer until selection is on CANDIDATE. - (helm-awhile (condition-case-unless-debug nil - (and (not (helm-pos-header-line-p)) - (helm-get-selection)) - (error nil)) - (if (string= it candidate) - (cl-return) - (helm-next-line)))) - -(defun helm-kill-ring-action-yank (_str) - "Insert concatenated marked candidates in current-buffer. - -When two prefix args are given prompt to choose separator, otherwise -use `helm-kill-ring-separator' as default." - (let ((marked (helm-marked-candidates)) - (sep (if (equal helm-current-prefix-arg '(16)) - (read-string "Separator: ") - helm-kill-ring-separator))) - (helm-kill-ring-action-yank-1 - (cl-loop for c in (butlast marked) - concat (concat c sep) into str - finally return (concat str (car (last marked))))))) - -(defun helm-kill-ring-action-yank-1 (str) - "Insert STR in `kill-ring' and set STR to the head. - -When called with a prefix arg, point and mark are exchanged without -activating region. -If this action is executed just after `yank', -replace with STR as yanked string." - (let ((yank-fn (lambda (&optional before yank-pop) - (insert-for-yank str) - ;; Set the window start back where it was in - ;; the yank command, if possible. - (when yank-pop - (set-window-start (selected-window) yank-window-start t)) - (when (or (equal helm-current-prefix-arg '(4)) before) - ;; Same as exchange-point-and-mark but without - ;; activating region. - (goto-char (prog1 (mark t) - (set-marker (mark-marker) - (point) - helm-current-buffer))))))) - ;; Prevent inserting and saving highlighted items. - (set-text-properties 0 (length str) nil str) - (with-helm-current-buffer - (unwind-protect - (progn - (setq kill-ring (delete str kill-ring)) - ;; Adding a `delete-selection' property - ;; to `helm-kill-ring-action' is not working - ;; because `this-command' will be `helm-maybe-exit-minibuffer', - ;; so use this workaround (Issue #1520). - (when (and (region-active-p) delete-selection-mode) - (delete-region (region-beginning) (region-end))) - (if (not (eq (helm-attr 'last-command helm-source-kill-ring) 'yank)) - (progn - ;; Ensure mark is at beginning of inserted text. - (push-mark) - ;; When yanking in a helm minibuffer we need a small - ;; delay to detect the mark in previous minibuffer. [1] - (run-with-timer 0.01 nil yank-fn)) - ;; from `yank-pop' - (let ((inhibit-read-only t) - (before (< (point) (mark t)))) - (if before - (funcall (or yank-undo-function 'delete-region) (point) (mark t)) - (funcall (or yank-undo-function 'delete-region) (mark t) (point))) - (setq yank-undo-function nil) - (set-marker (mark-marker) (point) helm-current-buffer) - ;; Same as [1] but use the same mark and point as in - ;; the initial yank according to BEFORE even if no - ;; prefix arg is given. - (run-with-timer 0.01 nil yank-fn before 'pop)))) - (kill-new str))))) -(define-obsolete-function-alias 'helm-kill-ring-action 'helm-kill-ring-action-yank "2.4.0") - -(defun helm-kill-ring-action-delete (_candidate) - "Delete marked candidates from `kill-ring'." - (cl-loop for c in (helm-marked-candidates) - do (setq kill-ring - (delete c kill-ring)))) - -(defun helm-kill-ring-persistent-delete (_candidate) - (unwind-protect - (cl-loop for c in (helm-marked-candidates) - do (progn - (helm-preselect (format "^%s" (regexp-quote c))) - (setq kill-ring (delete c kill-ring)) - (helm-delete-current-selection) - (helm--remove-marked-and-update-mode-line c))) - (with-helm-buffer - (setq helm-marked-candidates nil - helm-visible-mark-overlays nil)) - (helm-force-update (helm-aif (helm-get-selection nil t) (regexp-quote it))))) - -(defun helm-kill-ring-run-persistent-delete () - "Delete current candidate without quitting." - (interactive) - (with-helm-alive-p - (helm-attrset 'quick-delete '(helm-kill-ring-persistent-delete . never-split)) - (helm-execute-persistent-action 'quick-delete))) -(put 'helm-kill-ring-run-persistent-delete 'helm-only t) - -(defun helm-kill-ring-delete () - "Delete marked candidates from `kill-ring'. - -This is a command for `helm-kill-ring-map'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action 'helm-kill-ring-action-delete))) -(put 'helm-kill-ring-delete 'helm-only t) - - -;;;; -;; DO NOT use these sources with other sources use -;; the commands `helm-mark-ring', `helm-global-mark-ring' or -;; `helm-all-mark-rings' instead. - -(defun helm-mark-ring-line-string-at-pos (pos) - "Return line string at position POS." - (save-excursion - (goto-char pos) - (forward-line 0) - (let ((line (car (split-string (thing-at-point 'line) "[\n\r]")))) - (remove-text-properties 0 (length line) '(read-only) line) - (if (string= "" line) - "" - line)))) - -(defun helm-mark-ring-get-candidates () - (with-helm-current-buffer - (cl-loop with marks = (if (mark t) - (cons (mark-marker) mark-ring) - mark-ring) - for marker in marks - with max-line-number = (line-number-at-pos (point-max)) - with width = (length (number-to-string max-line-number)) - for m = (format (concat "%" (number-to-string width) "d: %s") - (line-number-at-pos marker) - (helm-mark-ring-line-string-at-pos marker)) - unless (and recip (assoc m recip)) - collect (cons m marker) into recip - finally return recip))) - -(defun helm-mark-ring-default-action (candidate) - (let ((target (copy-marker candidate))) - (helm-aif (marker-buffer candidate) - (progn - (switch-to-buffer it) - (helm-log-run-hook 'helm-goto-line-before-hook) - (helm-match-line-cleanup) - (with-helm-current-buffer - (unless helm-yank-point (setq helm-yank-point (point)))) - (helm-goto-char target) - (helm-highlight-current-line)) - ;; marker points to no buffer, no need to dereference it, just - ;; delete it. - (setq mark-ring (delete target mark-ring)) - (error "Marker points to no buffer")))) - -(defvar helm-source-mark-ring - (helm-build-sync-source "mark-ring" - :candidates #'helm-mark-ring-get-candidates - :action '(("Goto line" . helm-mark-ring-default-action)) - :persistent-help "Show this line" - :group 'helm-ring)) - -;;; Global-mark-ring -(defvar helm-source-global-mark-ring - (helm-build-sync-source "global-mark-ring" - :candidates #'helm-global-mark-ring-get-candidates - :action '(("Goto line" . helm-mark-ring-default-action)) - :persistent-help "Show this line" - :group 'helm-ring)) - -(defun helm-global-mark-ring-format-buffer (marker) - (with-current-buffer (marker-buffer marker) - (goto-char marker) - (forward-line 0) - (let ((line (pcase (thing-at-point 'line) - ((and line (pred stringp) - (guard (not (string-match-p "\\`\n?\\'" line)))) - (car (split-string line "[\n\r]"))) - (_ "")))) - (remove-text-properties 0 (length line) '(read-only) line) - (format "%7d:%s: %s" - (line-number-at-pos) (marker-buffer marker) line)))) - -(defun helm-global-mark-ring-get-candidates () - (let ((marks global-mark-ring)) - (when marks - (cl-loop for marker in marks - for mb = (marker-buffer marker) - for gm = (unless (or (string-match "^ " (format "%s" mb)) - (null mb)) - (helm-global-mark-ring-format-buffer marker)) - when (and gm (not (assoc gm recip))) - collect (cons gm marker) into recip - finally return recip)))) - -;;;; -;;; Insert from register -(defvar helm-source-register - (helm-build-sync-source "Registers" - :candidates #'helm-register-candidates - :action-transformer #'helm-register-action-transformer - :persistent-help "" - :multiline t - :action '(("Delete Register(s)" . - (lambda (_candidate) - (cl-loop for candidate in (helm-marked-candidates) - for register = (car candidate) - do (setq register-alist - (delq (assoc register register-alist) - register-alist)))))) - :group 'helm-ring) - "See (info \"(emacs)Registers\")") - -(defun helm-register-candidates () - "Collecting register contents and appropriate commands." - (cl-loop for (char . val) in register-alist - for key = (single-key-description char) - for string-actions = - (cond - ((numberp val) - (list (int-to-string val) - 'insert-register - 'increment-register)) - ((markerp val) - (let ((buf (marker-buffer val))) - (if (null buf) - (list "a marker in no buffer") - (list (concat - "a buffer position:" - (buffer-name buf) - ", position " - (int-to-string (marker-position val))) - 'jump-to-register - 'insert-register)))) - ((and (consp val) (window-configuration-p (car val))) - (list "window configuration." - 'jump-to-register)) - ((and (vectorp val) - (fboundp 'undo-tree-register-data-p) - (undo-tree-register-data-p (elt val 1))) - (list - "Undo-tree entry." - 'undo-tree-restore-state-from-register)) - ((or (and (vectorp val) (eq 'registerv (aref val 0))) - (and (consp val) (frame-configuration-p (car val)))) - (list "frame configuration." - 'jump-to-register)) - ((and (consp val) (eq (car val) 'file)) - (list (concat "file:" - (prin1-to-string (cdr val)) - ".") - 'jump-to-register)) - ((and (consp val) (eq (car val) 'file-query)) - (list (concat "file:a file-query reference: file " - (car (cdr val)) - ", position " - (int-to-string (car (cdr (cdr val)))) - ".") - 'jump-to-register)) - ((consp val) - (let ((lines (format "%4d" (length val)))) - (list (format "%s: %s\n" lines - (truncate-string-to-width - (mapconcat 'identity (list (car val)) - "^J") - (- (window-width) 15))) - 'insert-register))) - ((stringp val) - (list - (concat (substring-no-properties - val 0 (min (length val) helm-register-max-offset)) - (if (> (length val) helm-register-max-offset) - "[...]" "")) - 'insert-register - 'kill-new - 'append-to-register - 'prepend-to-register))) - unless (null string-actions) ; Fix Issue #1107. - collect (cons (format "Register %3s:\n %s" key (car string-actions)) - (cons char (cdr string-actions))))) - -(defun helm-register-action-transformer (actions register-and-functions) - "Decide actions by the contents of register." - (cl-loop with func-actions = - '((insert-register - "Insert Register" . - (lambda (c) (insert-register (car c)))) - (kill-new - "Kill Register" . - (lambda (c) (with-temp-buffer - (insert-register (car c)) - (kill-new (buffer-string))))) - (jump-to-register - "Jump to Register" . - (lambda (c) (jump-to-register (car c)))) - (append-to-register - "Append Region to Register" . - (lambda (c) (append-to-register - (car c) (region-beginning) (region-end)))) - (prepend-to-register - "Prepend Region to Register" . - (lambda (c) (prepend-to-register - (car c) (region-beginning) (region-end)))) - (increment-register - "Increment Prefix Arg to Register" . - (lambda (c) (increment-register - helm-current-prefix-arg (car c)))) - (undo-tree-restore-state-from-register - "Restore Undo-tree register" . - (lambda (c) (and (fboundp 'undo-tree-restore-state-from-register) - (undo-tree-restore-state-from-register (car c)))))) - for func in (cdr register-and-functions) - when (assq func func-actions) - collect (cdr it) into transformer-actions - finally return (append transformer-actions actions))) - -;;;###autoload -(defun helm-mark-ring () - "Preconfigured `helm' for `helm-source-mark-ring'." - (interactive) - (helm :sources 'helm-source-mark-ring - :resume 'noresume - :buffer "*helm mark*")) - -;;;###autoload -(defun helm-global-mark-ring () - "Preconfigured `helm' for `helm-source-global-mark-ring'." - (interactive) - (helm :sources 'helm-source-global-mark-ring - :resume 'noresume - :buffer "*helm global mark*")) - -;;;###autoload -(defun helm-all-mark-rings () - "Preconfigured `helm' for `helm-source-global-mark-ring' and \ -`helm-source-mark-ring'." - (interactive) - (helm :sources '(helm-source-mark-ring - helm-source-global-mark-ring) - :resume 'noresume - :buffer "*helm mark ring*")) - -;;;###autoload -(defun helm-register () - "Preconfigured `helm' for Emacs registers." - (interactive) - (helm :sources 'helm-source-register - :resume 'noresume - :buffer "*helm register*")) - -;;;###autoload -(defun helm-show-kill-ring () - "Preconfigured `helm' for `kill-ring'. -It is drop-in replacement of `yank-pop'. - -First call open the kill-ring browser, next calls move to next line." - (interactive) - (setq helm-kill-ring--truncated-flag nil) - (let ((enable-recursive-minibuffers t)) - (helm :sources helm-source-kill-ring - :buffer "*helm kill ring*" - :resume 'noresume - :allow-nest t))) - -;;;###autoload -(defun helm-execute-kmacro () - "Preconfigured helm for keyboard macros. -Define your macros with `f3' and `f4'. -See (info \"(emacs) Keyboard Macros\") for detailed infos. -This command is useful when used with persistent action." - (interactive) - (let ((helm-quit-if-no-candidate - (lambda () (message "No kbd macro has been defined")))) - (helm :sources - (helm-build-sync-source "Kmacro" - :candidates (lambda () - (helm-fast-remove-dups - (cons (kmacro-ring-head) - kmacro-ring) - :test 'equal)) - :multiline t - :candidate-transformer - (lambda (candidates) - (cl-loop for c in candidates collect - (propertize (help-key-description (car c) nil) - 'helm-realvalue c))) - :persistent-help "Execute kmacro" - :help-message 'helm-kmacro-help-message - :action - (helm-make-actions - "Execute kmacro (`C-u ' to execute times)" - 'helm-kbd-macro-execute - "Concat marked macros" - 'helm-kbd-macro-concat-macros - "Delete marked macros" - 'helm-kbd-macro-delete-macro - "Edit marked macro" - 'helm-kbd-macro-edit-macro) - :group 'helm-ring) - :buffer "*helm kmacro*"))) - -(defun helm-kbd-macro-execute (candidate) - ;; Move candidate on top of list for next use. - (setq kmacro-ring (delete candidate kmacro-ring)) - (kmacro-push-ring) - (kmacro-split-ring-element candidate) - (kmacro-exec-ring-item - candidate helm-current-prefix-arg)) - -(defun helm-kbd-macro-concat-macros (_candidate) - (let ((mkd (helm-marked-candidates))) - (when (cdr mkd) - (kmacro-push-ring) - (setq last-kbd-macro - (mapconcat 'identity - (cl-loop for km in mkd - if (vectorp km) - append (cl-loop for k across km collect - (key-description (vector k))) - into result - else collect (car km) into result - finally return result) - ""))))) - -(defun helm-kbd-macro-delete-macro (_candidate) - (let ((mkd (helm-marked-candidates))) - (kmacro-push-ring) - (cl-loop for km in mkd - do (setq kmacro-ring (delete km kmacro-ring))) - (kmacro-pop-ring1))) - -(defun helm-kbd-macro-edit-macro (candidate) - (kmacro-push-ring) - (setq kmacro-ring (delete candidate kmacro-ring)) - (kmacro-split-ring-element candidate) - (kmacro-edit-macro)) - -(provide 'helm-ring) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-ring.el ends here diff --git a/elpa/helm-20191031.725/helm-semantic.el b/elpa/helm-20191031.725/helm-semantic.el deleted file mode 100644 index f5691244..00000000 --- a/elpa/helm-20191031.725/helm-semantic.el +++ /dev/null @@ -1,236 +0,0 @@ -;;; helm-semantic.el --- Helm interface for Semantic -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2017 Daniel Hackney -;; 2012 ~ 2019 Thierry Volpiatto - -;; Author: Daniel Hackney - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Commentary: - -;; Uses `candidates-in-buffer' for speed. - -;;; Code: - -(require 'cl-lib) -(require 'semantic) -(require 'helm-help) -(require 'helm-imenu) - -(declare-function pulse-momentary-highlight-one-line "pulse.el" (point &optional face)) - -(defgroup helm-semantic nil - "Semantic tags related libraries and applications for helm." - :group 'helm) - -(defcustom helm-semantic-display-style - '((python-mode . semantic-format-tag-summarize) - (c-mode . semantic-format-tag-concise-prototype-c-mode) - (emacs-lisp-mode . semantic-format-tag-abbreviate-emacs-lisp-mode)) - "Function to present a semantic tag according to `major-mode'. - -It is an alist where the `car' of each element is a `major-mode' and -the `cdr' a `semantic-format-tag-*' function. - -If no function is found for current `major-mode', fall back to -`semantic-format-tag-summarize' default function. - -You can have more or less informations depending of the `semantic-format-tag-*' -function you choose. - -All the supported functions are prefixed with \"semantic-format-tag-\", -you have completion on these functions with `C-M i' in the customize interface." - :group 'helm-semantic - :type '(alist :key-type symbol :value-type symbol)) - -;;; keymap -(defvar helm-semantic-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - map)) - -(defcustom helm-semantic-lynx-style-map nil - "Use Arrow keys to jump to occurences." - :group 'helm-semantic - :type 'boolean - :set (lambda (var val) - (set var val) - (if val - (progn - (define-key helm-semantic-map (kbd "") 'helm-execute-persistent-action) - (define-key helm-semantic-map (kbd "") 'helm-maybe-exit-minibuffer)) - (define-key helm-semantic-map (kbd "") nil) - (define-key helm-semantic-map (kbd "") nil)))) - -;; Internals vars -(defvar helm-semantic--tags-cache nil) - -(defun helm-semantic--fetch-candidates (tags depth &optional class) - "Write the contents of TAGS to the current buffer." - (let ((class class) cur-type - (stylefn (or (with-helm-current-buffer - (assoc-default major-mode helm-semantic-display-style)) - #'semantic-format-tag-summarize))) - (cl-dolist (tag tags) - (when (listp tag) - (cl-case (setq cur-type (semantic-tag-class tag)) - ((function variable type) - (let ((spaces (make-string (* depth 2) ?\s)) - (type-p (eq cur-type 'type))) - (unless (and (> depth 0) (not type-p)) - (setq class nil)) - (insert - (if (and class (not type-p)) - (format "%s%s(%s) " - spaces (if (< depth 2) "" "├►") class) - spaces) - ;; Save the tag for later - (propertize (funcall stylefn tag nil t) - 'semantic-tag tag) - "\n") - (and type-p (setq class (car tag))) - ;; Recurse to children - (unless (eq cur-type 'function) - (helm-semantic--fetch-candidates - (semantic-tag-components tag) (1+ depth) class)))) - - ;; Don't do anything with packages or includes for now - ((package include) - (insert - (propertize (funcall stylefn tag nil t) - 'semantic-tag tag) - "\n") - ) - ;; Catch-all - (t)))))) - -(defun helm-semantic-default-action (_candidate &optional persistent) - ;; By default, helm doesn't pass on the text properties of the selection. - ;; Fix this. - (helm-log-run-hook 'helm-goto-line-before-hook) - (with-current-buffer helm-buffer - (when (looking-at " ") - (goto-char (next-single-property-change - (point-at-bol) 'semantic-tag nil (point-at-eol)))) - (let ((tag (get-text-property (point) 'semantic-tag))) - (semantic-go-to-tag tag) - (unless persistent - (pulse-momentary-highlight-one-line (point)))))) - -(defun helm-semantic--maybe-set-needs-update () - (with-helm-current-buffer - (when (semantic-parse-tree-needs-update-p) - (semantic-parse-tree-set-needs-update)))) - -(defvar helm-source-semantic nil) - -(defclass helm-semantic-source (helm-source-in-buffer) - ((init :initform (lambda () - (helm-semantic--maybe-set-needs-update) - (setq helm-semantic--tags-cache (semantic-fetch-tags)) - (with-current-buffer (helm-candidate-buffer 'global) - (let ((major-mode (with-helm-current-buffer major-mode))) - (helm-semantic--fetch-candidates helm-semantic--tags-cache 0))))) - (get-line :initform 'buffer-substring) - (persistent-help :initform "Show this entry") - (keymap :initform 'helm-semantic-map) - (help-message :initform 'helm-semantic-help-message) - (persistent-action :initform (lambda (elm) - (helm-semantic-default-action elm t) - (helm-highlight-current-line))) - (action :initform 'helm-semantic-default-action))) - -(defcustom helm-semantic-fuzzy-match nil - "Enable fuzzy matching in `helm-source-semantic'." - :group 'helm-semantic - :type 'boolean - :set (lambda (var val) - (set var val) - (setq helm-source-semantic - (helm-make-source "Semantic Tags" 'helm-semantic-source - :fuzzy-match helm-semantic-fuzzy-match)))) - -;;;###autoload -(defun helm-semantic (arg) - "Preconfigured `helm' for `semantic'. -If ARG is supplied, pre-select symbol at point instead of current" - (interactive "P") - (let ((tag (helm-aif (car (semantic-current-tag-parent)) - (let ((curtag (car (semantic-current-tag)))) - (if (string= it curtag) - (format "\\_<%s\\_>" curtag) - (cons (format "\\_<%s\\_>" it) - (format "\\_<%s\\_>" curtag)))) - (format "\\_<%s\\_>" (car (semantic-current-tag)))))) - (unless helm-source-semantic - (setq helm-source-semantic - (helm-make-source "Semantic Tags" 'helm-semantic-source - :fuzzy-match helm-semantic-fuzzy-match))) - (helm :sources 'helm-source-semantic - :candidate-number-limit 9999 - :preselect (if arg - (thing-at-point 'symbol) - tag) - :buffer "*helm semantic*"))) - -;;;###autoload -(defun helm-semantic-or-imenu (arg) - "Preconfigured helm for `semantic' or `imenu'. -If ARG is supplied, pre-select symbol at point instead of current -semantic tag in scope. - -If `semantic-mode' is active in the current buffer, then use -semantic for generating tags, otherwise fall back to `imenu'. -Fill in the symbol at point by default." - (interactive "P") - (unless helm-source-semantic - (setq helm-source-semantic - (helm-make-source "Semantic Tags" 'helm-semantic-source - :fuzzy-match helm-semantic-fuzzy-match))) - (unless helm-source-imenu - (setq helm-source-imenu - (helm-make-source "Imenu" 'helm-imenu-source - :fuzzy-match helm-imenu-fuzzy-match))) - (let* ((source (if (semantic-active-p) - 'helm-source-semantic - 'helm-source-imenu)) - (imenu-p (eq source 'helm-source-imenu)) - (imenu-auto-rescan imenu-p) - (str (thing-at-point 'symbol)) - (helm-execute-action-at-once-if-one - (and imenu-p - helm-imenu-execute-action-at-once-if-one)) - (tag (helm-aif (car (semantic-current-tag-parent)) - (let ((curtag (car (semantic-current-tag)))) - (if (string= it curtag) - (format "\\_<%s\\_>" curtag) - (cons (format "\\_<%s\\_>" it) - (format "\\_<%s\\_>" curtag)))) - (format "\\_<%s\\_>" (car (semantic-current-tag)))))) - (helm :sources source - :candidate-number-limit 9999 - :default (and imenu-p (list (concat "\\_<" (and str (regexp-quote str)) "\\_>") str)) - :preselect (if (or arg imenu-p) str tag) - :buffer "*helm semantic/imenu*"))) - -(provide 'helm-semantic) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-semantic.el ends here diff --git a/elpa/helm-20191031.725/helm-shell.el b/elpa/helm-20191031.725/helm-shell.el deleted file mode 100644 index 5f946dc5..00000000 --- a/elpa/helm-20191031.725/helm-shell.el +++ /dev/null @@ -1,44 +0,0 @@ -;;; helm-shell.el --- Shell prompt navigation for helm. -*- lexical-binding: t -*- - -;; Copyright (C) 2019 Pierre Neidhardt - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Commentary: -;; -;; This is superseded by helm-comint.el. - -;;; Code: -(require 'cl-lib) -(require 'helm) -(require 'helm-lib) -(require 'helm-help) -(require 'helm-elisp) -(require 'helm-comint) - -;;;###autoload -(defalias 'helm-shell-prompts 'helm-comint-prompts) - -;;;###autoload -(defalias 'helm-shell-prompts-all 'helm-comint-prompts-all) - -(provide 'helm-shell) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-shell ends here diff --git a/elpa/helm-20191031.725/helm-sys.el b/elpa/helm-20191031.725/helm-sys.el deleted file mode 100644 index cfe015ec..00000000 --- a/elpa/helm-20191031.725/helm-sys.el +++ /dev/null @@ -1,459 +0,0 @@ -;;; helm-sys.el --- System related functions for helm. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'cl-lib) -(require 'helm) -(require 'helm-help) -(require 'helm-utils) - - -(defgroup helm-sys nil - "System related helm library." - :group 'helm) - -(defface helm-top-columns - '((t :inherit helm-header)) - "Face for helm help string in minibuffer." - :group 'helm-sys) - - -(defcustom helm-top-command - (cl-case system-type - (darwin "env COLUMNS=%s ps -axo pid,user,pri,nice,ucomm,tty,start_time,vsz,%%cpu,%%mem,etime,command") - (t "env COLUMNS=%s top -b -n 1")) - "Top command used to display output of top. -A format string where %s will be replaced with `frame-width'. - -To use 'top' command, a version supporting batch mode (-b option) is needed. -On Mac OSX 'top' command doesn't support this, so ps command -is used instead by default. -Normally 'top' command output have 12 columns, but in some versions you may -have less than this, so you can either customize top to use 12 columns with the -interactives 'f' and 'W' commands of top, or modify -`helm-top-sort-columns-alist' to fit with the number of columns -your 'top' command is using. - -If you modify 'ps' command be sure that 'pid' comes in first -and \"env COLUMNS=%s\" is specified at beginning of command. -Ensure also that no elements contain spaces (e.g use start_time and not start). -Same as for 'top' you can customize `helm-top-sort-columns-alist' to make sort commands -working properly according to your settings." - :group 'helm-sys - :type 'string) - -(defcustom helm-top-sort-columns-alist '((com . 11) - (mem . 9) - (cpu . 8) - (user . 1)) - "Allow defining which column to use when sorting output of top/ps command. -Only com, mem, cpu and user are sorted, so no need to put something else there, -it will have no effect. -Note that column numbers are counted from zero, i.e column 1 is the nth 0 column." - :group 'helm-sys - :type '(alist :key-type symbol :value-type (integer :tag "Column number"))) - -(defcustom helm-top-poll-delay 1.5 - "Helm top poll after this delay when `helm-top-poll-mode' is enabled. -The minimal delay allowed is 1.5, if less than this helm-top will use 1.5." - :group 'helm-sys - :type 'float) - -(defcustom helm-top-poll-delay-post-command 1.0 - "Helm top stop polling during this delay. -This delay is additioned to `helm-top-poll-delay' after emacs stop -being idle." - :group 'helm-sys - :type 'float) - -(defcustom helm-top-poll-preselection 'linum - "Stay on same line or follow candidate when `helm-top-poll' update display. -Possible values are 'candidate or 'linum. -This affect also sorting functions in the same way." - :group'helm-sys - :type '(radio :tag "Preferred preselection action for helm-top" - (const :tag "Follow candidate" candidate) - (const :tag "Stay on same line" linum))) - -;;; Top (process) -;; -;; -(defvar helm-top-sort-fn nil) -(defvar helm-top-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "M-P") 'helm-top-run-sort-by-cpu) - (define-key map (kbd "M-C") 'helm-top-run-sort-by-com) - (define-key map (kbd "M-M") 'helm-top-run-sort-by-mem) - (define-key map (kbd "M-U") 'helm-top-run-sort-by-user) - map)) - -(defvar helm-top-after-init-hook nil - "Local hook for helm-top.") - -(defvar helm-top--poll-timer nil) - -(defun helm-top-poll (&optional no-update delay) - (when helm-top--poll-timer - (cancel-timer helm-top--poll-timer)) - (condition-case nil - (progn - (when (and (helm--alive-p) (null no-update)) - ;; Fix quitting while process is running - ;; by binding `with-local-quit' in init function - ;; Issue #1521. - (helm-force-update - (cl-ecase helm-top-poll-preselection - (candidate (replace-regexp-in-string - "[0-9]+" "[0-9]+" - (regexp-quote (helm-get-selection nil t)))) - (linum `(lambda () - (goto-char (point-min)) - (forward-line ,(helm-candidate-number-at-point))))))) - (setq helm-top--poll-timer - (run-with-idle-timer - (helm-aif (current-idle-time) - (time-add it (seconds-to-time - (or delay (helm-top--poll-delay)))) - (or delay (helm-top--poll-delay))) - nil - 'helm-top-poll))) - (quit (cancel-timer helm-top--poll-timer)))) - -(defun helm-top--poll-delay () - (max 1.5 helm-top-poll-delay)) - -(defun helm-top-poll-no-update () - (helm-top-poll t (+ (helm-top--poll-delay) - helm-top-poll-delay-post-command))) - -(defun helm-top-initialize-poll-hooks () - ;; When emacs is idle during say 20s - ;; the idle timer will run in 20+1.5 s. - ;; This is fine when emacs stays idle, because the next timer - ;; will run at 21.5+1.5 etc... so the display will be updated - ;; at every 1.5 seconds. - ;; But as soon as emacs looses its idleness, the next update - ;; will occur at say 21+1.5 s, so we have to reinitialize - ;; the timer at 0+1.5. - (add-hook 'post-command-hook 'helm-top-poll-no-update) - (add-hook 'focus-in-hook 'helm-top-poll-no-update)) - -;;;###autoload -(define-minor-mode helm-top-poll-mode - "Refresh automatically helm top buffer once enabled." - :group 'helm-top - :global t - (if helm-top-poll-mode - (progn - (add-hook 'helm-top-after-init-hook 'helm-top-poll-no-update) - (add-hook 'helm-top-after-init-hook 'helm-top-initialize-poll-hooks)) - (remove-hook 'helm-top-after-init-hook 'helm-top-poll-no-update) - (remove-hook 'helm-top-after-init-hook 'helm-top-initialize-poll-hooks))) - -(defvar helm-source-top - (helm-build-in-buffer-source "Top" - :header-name (lambda (name) - (concat name (if helm-top-poll-mode - " (auto updating)" - " (Press C-c C-u to refresh)"))) - :init #'helm-top-init - :after-init-hook 'helm-top-after-init-hook - :cleanup (lambda () - (when helm-top--poll-timer - (cancel-timer helm-top--poll-timer)) - (remove-hook 'post-command-hook 'helm-top-poll-no-update) - (remove-hook 'focus-in-hook 'helm-top-poll-no-update)) - :display-to-real #'helm-top-display-to-real - :persistent-action '(helm-top-sh-persistent-action . never-split) - :persistent-help "SIGTERM" - :help-message 'helm-top-help-message - :mode-line 'helm-top-mode-line - :follow 'never - :keymap helm-top-map - :filtered-candidate-transformer #'helm-top-sort-transformer - :action-transformer #'helm-top-action-transformer - :group 'helm-sys)) - -(defvar helm-top--line nil) -(defun helm-top-transformer (candidates _source) - "Transformer for `helm-top'. -Return empty string for non--valid candidates." - (cl-loop for disp in candidates collect - (cond ((string-match "^ *[0-9]+" disp) disp) - ((string-match "^ *PID" disp) - (setq helm-top--line (cons (propertize disp 'face 'helm-top-columns) ""))) - (t (cons disp ""))) - into lst - finally return (or (member helm-top--line lst) - (cons helm-top--line lst)))) - -(defun helm-top--skip-top-line () - (let* ((src (helm-get-current-source)) - (src-name (assoc-default 'name src))) - (helm-aif (and (stringp src-name) - (string= src-name "Top") - (helm-get-selection nil t src)) - (when (string-match-p "^ *PID" it) - (helm-next-line))))) - -(defun helm-top-action-transformer (actions _candidate) - "Action transformer for `top'. -Show actions only on line starting by a PID." - (let ((disp (helm-get-selection nil t))) - (cond ((string-match "\\` *[0-9]+" disp) - (list '("kill (SIGTERM)" . (lambda (_pid) - (helm-top-sh "TERM" (helm-top--marked-pids)))) - '("kill (SIGKILL)" . (lambda (_pid) - (helm-top-sh "KILL" (helm-top--marked-pids)))) - '("kill (SIGINT)" . (lambda (_pid) - (helm-top-sh "INT" (helm-top--marked-pids)))) - '("kill (Choose signal)" - . (lambda (_pid) - (let ((pids (helm-top--marked-pids))) - (helm-top-sh - (helm-comp-read (format "Kill %d pids with signal: " - (length pids)) - '("ALRM" "HUP" "INT" "KILL" "PIPE" "POLL" - "PROF" "TERM" "USR1" "USR2" "VTALRM" - "STKFLT" "PWR" "WINCH" "CHLD" "URG" - "TSTP" "TTIN" "TTOU" "STOP" "CONT" - "ABRT" "FPE" "ILL" "QUIT" "SEGV" - "TRAP" "SYS" "EMT" "BUS" "XCPU" "XFSZ") - :must-match t) - pids)))))) - (t actions)))) - -(defun helm-top--marked-pids () - (helm-remove-if-not-match "\\`[0-9]+\\'" (helm-marked-candidates))) - -(defun helm-top-sh (sig pids) - "Run kill shell command with signal SIG on PIDS for `helm-top'." - (message "kill -%s %s exited with status %s" - sig (mapconcat 'identity pids " ") - (apply #'call-process - "kill" nil nil nil (format "-%s" sig) pids))) - -(defun helm-top-sh-persistent-action (pid) - (helm-top-sh "TERM" (list pid)) - (helm-delete-current-selection)) - -(defun helm-top-init () - "Insert output of top command in candidate buffer." - (with-local-quit - (unless helm-top-sort-fn (helm-top-set-mode-line "CPU")) - (with-current-buffer (helm-candidate-buffer 'global) - (call-process-shell-command - (format helm-top-command (frame-width)) - nil (current-buffer))))) - -(defun helm-top-display-to-real (line) - "Return pid only from LINE." - (car (split-string line))) - -;; Sort top command - -(defun helm-top-set-mode-line (str) - (if (string-match "Sort:\\[\\(.*\\)\\] " helm-top-mode-line) - (setq helm-top-mode-line (replace-match str nil nil helm-top-mode-line 1)) - (setq helm-top-mode-line (concat (format "Sort:[%s] " str) helm-top-mode-line)))) - -(defun helm-top-sort-transformer (candidates source) - (helm-top-transformer - (if helm-top-sort-fn - (cl-loop for c in candidates - if (string-match "^ *[0-9]+" c) - collect c into pid-cands - else collect c into header-cands - finally return (append - header-cands - (sort pid-cands helm-top-sort-fn))) - candidates) - source)) - -(defun helm-top-sort-by-com (s1 s2) - (let* ((split-1 (split-string s1)) - (split-2 (split-string s2)) - (col (cdr (assq 'com helm-top-sort-columns-alist))) - (com-1 (nth col split-1)) - (com-2 (nth col split-2))) - (string< com-1 com-2))) - -(defun helm-top-sort-by-mem (s1 s2) - (let* ((split-1 (split-string s1)) - (split-2 (split-string s2)) - (col (cdr (assq 'mem helm-top-sort-columns-alist))) - (mem-1 (string-to-number (nth col split-1))) - (mem-2 (string-to-number (nth col split-2)))) - (> mem-1 mem-2))) - -(defun helm-top-sort-by-cpu (s1 s2) - (let* ((split-1 (split-string s1)) - (split-2 (split-string s2)) - (col (cdr (assq 'cpu helm-top-sort-columns-alist))) - (cpu-1 (string-to-number (nth col split-1))) - (cpu-2 (string-to-number (nth col split-2)))) - (> cpu-1 cpu-2))) - -(defun helm-top-sort-by-user (s1 s2) - (let* ((split-1 (split-string s1)) - (split-2 (split-string s2)) - (col (cdr (assq 'user helm-top-sort-columns-alist))) - (user-1 (nth col split-1)) - (user-2 (nth col split-2))) - (string< user-1 user-2))) - -(defun helm-top--preselect-fn () - (if (eq helm-top-poll-preselection 'linum) - `(lambda () - (goto-char (point-min)) - (forward-line ,(helm-candidate-number-at-point))) - (replace-regexp-in-string - "[0-9]+" "[0-9]+" - (regexp-quote (helm-get-selection nil t))))) - -(defun helm-top-run-sort-by-com () - (interactive) - (helm-top-set-mode-line "COM") - (setq helm-top-sort-fn 'helm-top-sort-by-com) - (helm-update (helm-top--preselect-fn))) - -(defun helm-top-run-sort-by-cpu () - (interactive) - (helm-top-set-mode-line "CPU") - ;; Force sorting by CPU even if some versions of top are using by - ;; default CPU sorting (Issue #1908). - (setq helm-top-sort-fn 'helm-top-sort-by-cpu) - (helm-update (helm-top--preselect-fn))) - -(defun helm-top-run-sort-by-mem () - (interactive) - (helm-top-set-mode-line "MEM") - (setq helm-top-sort-fn 'helm-top-sort-by-mem) - (helm-update (helm-top--preselect-fn))) - -(defun helm-top-run-sort-by-user () - (interactive) - (helm-top-set-mode-line "USER") - (setq helm-top-sort-fn 'helm-top-sort-by-user) - (helm-update (helm-top--preselect-fn))) - - -;;; X RandR resolution change -;; -;; -;;; FIXME I do not care multi-display. - -(defun helm-xrandr-info () - "Return a pair with current X screen number and current X display name." - (with-temp-buffer - (call-process "xrandr" nil (current-buffer) nil - "--current") - (let (screen output) - (goto-char (point-min)) - (save-excursion - (when (re-search-forward "\\(^Screen \\)\\([0-9]\\):" nil t) - (setq screen (match-string 2)))) - (when (re-search-forward "^\\(.*\\) connected" nil t) - (setq output (match-string 1))) - (list screen output)))) - -(defun helm-xrandr-screen () - "Return current X screen number." - (car (helm-xrandr-info))) - -(defun helm-xrandr-output () - "Return current X display name." - (cadr (helm-xrandr-info))) - -(defvar helm-source-xrandr-change-resolution - (helm-build-sync-source "Change Resolution" - :candidates - (lambda () - (with-temp-buffer - (call-process "xrandr" nil (current-buffer) nil - "--screen" (helm-xrandr-screen) "-q") - (goto-char 1) - (cl-loop while (re-search-forward " \\([0-9]+x[0-9]+\\)" nil t) - for mode = (match-string 1) - unless (member mode modes) - collect mode into modes - finally return modes))) - :action - (helm-make-actions "Change Resolution" - (lambda (mode) - (call-process "xrandr" nil nil nil - "--screen" (helm-xrandr-screen) - "--output" (helm-xrandr-output) - "--mode" mode))))) - - -;;; Emacs process -;; -;; -(defvar helm-source-emacs-process - (helm-build-sync-source "Emacs Process" - :init (lambda () - (let (tabulated-list-use-header-line) - (list-processes--refresh))) - :candidates (lambda () (mapcar #'process-name (process-list))) - :persistent-action (lambda (elm) - (delete-process (get-process elm)) - (helm-delete-current-selection)) - :persistent-help "Kill Process" - :action (helm-make-actions "Kill Process" - (lambda (_elm) - (cl-loop for p in (helm-marked-candidates) - do (delete-process (get-process p))))))) - - -;;;###autoload -(defun helm-top () - "Preconfigured `helm' for top command." - (interactive) - (add-hook 'helm-after-update-hook 'helm-top--skip-top-line) - (unwind-protect - (helm :sources 'helm-source-top - :buffer "*helm top*" :full-frame t - :candidate-number-limit 9999 - :preselect "^\\s-*[0-9]+" - :truncate-lines helm-show-action-window-other-window) - (remove-hook 'helm-after-update-hook 'helm-top--skip-top-line))) - -;;;###autoload -(defun helm-list-emacs-process () - "Preconfigured `helm' for emacs process." - (interactive) - (helm-other-buffer 'helm-source-emacs-process "*helm process*")) - -;;;###autoload -(defun helm-xrandr-set () - "Preconfigured helm for xrandr." - (interactive) - (helm :sources 'helm-source-xrandr-change-resolution - :buffer "*helm xrandr*")) - -(provide 'helm-sys) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-sys.el ends here diff --git a/elpa/helm-20191031.725/helm-tags.el b/elpa/helm-20191031.725/helm-tags.el deleted file mode 100644 index 782e87b4..00000000 --- a/elpa/helm-20191031.725/helm-tags.el +++ /dev/null @@ -1,348 +0,0 @@ -;;; helm-tags.el --- Helm for Etags. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'cl-lib) -(require 'helm) -(require 'helm-help) -(require 'helm-utils) -(require 'helm-grep) - - -(defgroup helm-tags nil - "Tags related Applications and libraries for Helm." - :group 'helm) - -(defcustom helm-etags-tag-file-name "TAGS" - "Etags tag file name." - :type 'string - :group 'helm-tags) - -(defcustom helm-etags-tag-file-search-limit 10 - "The limit level of directory to search tag file. -Don't search tag file deeply if outside this value." - :type 'number - :group 'helm-tags) - -(defcustom helm-etags-match-part-only 'tag - "Allow choosing the tag part of CANDIDATE in `helm-source-etags-select'. -A tag looks like this: - filename: \(defun foo -You can choose matching against the tag part (i.e \"(defun foo\"), -or against the whole candidate (i.e \"(filename:5:(defun foo\")." - :type '(choice - (const :tag "Match only tag" tag) - (const :tag "Match all file+tag" all)) - :group 'helm-tags) - -(defcustom helm-etags-execute-action-at-once-if-one t - "Whether to jump straight to the selected tag if there's only -one match." - :type 'boolean - :group 'helm-tags) - - -(defgroup helm-tags-faces nil - "Customize the appearance of helm-tags faces." - :prefix "helm-" - :group 'helm-tags - :group 'helm-faces) - -(defface helm-etags-file - '((t (:foreground "Lightgoldenrod4" - :underline t))) - "Face used to highlight etags filenames." - :group 'helm-tags-faces) - - -;;; Etags -;; -;; -(defun helm-etags-run-switch-other-window () - "Run switch to other window action from `helm-source-etags-select'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action - (lambda (c) - (helm-etags-action-goto 'find-file-other-window c))))) -(put 'helm-etags-run-switch-other-window 'helm-only t) - -(defun helm-etags-run-switch-other-frame () - "Run switch to other frame action from `helm-source-etags-select'." - (interactive) - (with-helm-alive-p - (helm-exit-and-execute-action - (lambda (c) - (helm-etags-action-goto 'find-file-other-frame c))))) -(put 'helm-etags-run-switch-other-frame 'helm-only t) - -(defvar helm-etags-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "M-") 'helm-goto-next-file) - (define-key map (kbd "M-") 'helm-goto-precedent-file) - (define-key map (kbd "C-c o") 'helm-etags-run-switch-other-window) - (define-key map (kbd "C-c C-o") 'helm-etags-run-switch-other-frame) - map) - "Keymap used in Etags.") - -(defvar helm-etags-mtime-alist nil - "Store the last modification time of etags files here.") -(defvar helm-etags-cache (make-hash-table :test 'equal) - "Cache content of etags files used here for faster access.") - -(defun helm-etags-get-tag-file (&optional directory) - "Return the path of etags file if found. -Lookes recursively in parents directorys for a -`helm-etags-tag-file-name' file." - ;; Get tag file from `default-directory' or upper directory. - (let ((current-dir (helm-etags-find-tag-file-directory - (or directory default-directory)))) - ;; Return nil if not find tag file. - (when current-dir - (expand-file-name helm-etags-tag-file-name current-dir)))) - -(defun helm-etags-all-tag-files () - "Return files from the following sources; - 1) An automatically located file in the parent directories, by `helm-etags-get-tag-file'. - 2) `tags-file-name', which is commonly set by `find-tag' command. - 3) `tags-table-list' which is commonly set by `visit-tags-table' command." - (helm-fast-remove-dups - (delq nil - (append (list (helm-etags-get-tag-file) - tags-file-name) - tags-table-list)) - :test 'equal)) - -(defun helm-etags-find-tag-file-directory (current-dir) - "Try to find the directory containing tag file. -If not found in CURRENT-DIR search in upper directory." - (let ((file-exists? (lambda (dir) - (let ((tag-path (expand-file-name - helm-etags-tag-file-name dir))) - (and (stringp tag-path) - (file-regular-p tag-path) - (file-readable-p tag-path)))))) - (cl-loop with count = 0 - until (funcall file-exists? current-dir) - ;; Return nil if outside the value of - ;; `helm-etags-tag-file-search-limit'. - if (= count helm-etags-tag-file-search-limit) - do (cl-return nil) - ;; Or search upper directories. - else - do (cl-incf count) - (setq current-dir (expand-file-name (concat current-dir "../"))) - finally return current-dir))) - -(defun helm-etags-get-header-name (_x) - "Create header name for this helm etags session." - (concat "Etags in " - (with-helm-current-buffer - (helm-etags-get-tag-file)))) - -(defun helm-etags-create-buffer (file) - "Create the `helm-buffer' based on contents of etags tag FILE." - (let* (max - (split (with-temp-buffer - (insert-file-contents file) - (prog1 - (split-string (buffer-string) "\n" 'omit-nulls) - (setq max (line-number-at-pos (point-max)))))) - (progress-reporter (make-progress-reporter "Loading tag file..." 0 max))) - (cl-loop - with fname - with cand - for i in split for count from 0 - for elm = (unless (string-match "^\x0c" i) ;; "^L" - (helm-aif (string-match "\177" i) ;; "^?" - (substring i 0 it) - i)) - for linum = (when (string-match "[0-9]+,?[0-9]*$" i) - (car (split-string (match-string 0 i) ","))) - do (cond ((and elm (string-match "^\\([^,]+\\),[0-9]+$" elm)) - (setq fname (propertize (match-string 1 elm) - 'face 'helm-etags-file))) - (elm (setq cand (format "%s:%s:%s" fname linum elm))) - (t (setq cand nil))) - when cand do (progn - (insert (propertize (concat cand "\n") 'linum linum)) - (progress-reporter-update progress-reporter count))))) - -(defun helm-etags-init () - "Feed `helm-buffer' using `helm-etags-cache' or tag file. -If no entry in cache, create one." - (let ((tagfiles (helm-etags-all-tag-files))) - (when tagfiles - (with-current-buffer (helm-candidate-buffer 'global) - (dolist (f tagfiles) - (helm-aif (gethash f helm-etags-cache) - ;; An entry is present in cache, insert it. - (insert it) - ;; No entry, create a new buffer using content of tag file (slower). - (helm-etags-create-buffer f) - ;; Store content of buffer in cache. - (puthash f (buffer-string) helm-etags-cache) - ;; Store or set the last modification of tag file. - (helm-aif (assoc f helm-etags-mtime-alist) - ;; If an entry exists modify it. - (setcdr it (helm-etags-mtime f)) - ;; No entry create a new one. - (cl-pushnew (cons f (helm-etags-mtime f)) - helm-etags-mtime-alist - :test 'equal)))))))) - -(defvar helm-source-etags-select nil - "Helm source for Etags.") - -(defun helm-etags-build-source () - (helm-build-in-buffer-source "Etags" - :header-name 'helm-etags-get-header-name - :init 'helm-etags-init - :get-line 'buffer-substring - :match-part (lambda (candidate) - ;; Match only the tag part of CANDIDATE - ;; and not the filename. - (cl-case helm-etags-match-part-only - (tag (cl-caddr (helm-grep-split-line candidate))) - (t candidate))) - :fuzzy-match helm-etags-fuzzy-match - :help-message 'helm-etags-help-message - :keymap helm-etags-map - :action '(("Go to tag" . (lambda (c) - (helm-etags-action-goto 'find-file c))) - ("Go to tag in other window" . (lambda (c) - (helm-etags-action-goto - 'find-file-other-window - c))) - ("Go to tag in other frame" . (lambda (c) - (helm-etags-action-goto - 'find-file-other-frame - c)))) - :group 'helm-tags - :persistent-help "Go to line" - :persistent-action (lambda (candidate) - (helm-etags-action-goto 'find-file candidate) - (helm-highlight-current-line)))) - -(defcustom helm-etags-fuzzy-match nil - "Use fuzzy matching in `helm-etags-select'." - :group 'helm-tags - :type 'boolean - :set (lambda (var val) - (set var val) - (setq helm-source-etags-select - (helm-etags-build-source)))) - -(defvar find-tag-marker-ring) - -(defsubst helm-etags--file-from-tag (fname) - (cl-loop for ext in - (cons "" (remove "" tags-compression-info-list)) - for file = (concat fname ext) - when (file-exists-p file) - return file)) - -(defun helm-etags-action-goto (switcher candidate) - "Helm default action to jump to an etags entry in other window." - (require 'etags) - (deactivate-mark t) - (helm-log-run-hook 'helm-goto-line-before-hook) - (let* ((split (helm-grep-split-line candidate)) - (fname (cl-loop for tagf being the hash-keys of helm-etags-cache - for f = (expand-file-name - (car split) (file-name-directory tagf)) - ;; Try to find an existing file, possibly compressed. - when (helm-etags--file-from-tag f) - return it)) - (elm (cl-caddr split)) - (linum (string-to-number (cadr split)))) - (if (null fname) - (error "file %s not found" fname) - (ring-insert find-tag-marker-ring (point-marker)) - (funcall switcher fname) - (helm-goto-line linum t) - (when (search-forward elm nil t) - (goto-char (match-beginning 0)))))) - -(defun helm-etags-mtime (file) - "Last modification time of etags tag FILE." - (cadr (nth 5 (file-attributes file)))) - -(defun helm-etags-file-modified-p (file) - "Check if tag FILE have been modified in this session. -If FILE is nil return nil." - (let ((last-modif (and file - (assoc-default file helm-etags-mtime-alist)))) - (and last-modif - (/= last-modif (helm-etags-mtime file))))) - -;;;###autoload -(defun helm-etags-select (reinit) - "Preconfigured helm for etags. -If called with a prefix argument REINIT -or if any of the tag files have been modified, reinitialize cache. - -This function aggregates three sources of tag files: - - 1) An automatically located file in the parent directories, - by `helm-etags-get-tag-file'. - 2) `tags-file-name', which is commonly set by `find-tag' command. - 3) `tags-table-list' which is commonly set by `visit-tags-table' command." - (interactive "P") - (let ((tag-files (helm-etags-all-tag-files)) - (helm-execute-action-at-once-if-one - helm-etags-execute-action-at-once-if-one) - (str (if (region-active-p) - (buffer-substring-no-properties - (region-beginning) (region-end)) - (thing-at-point 'symbol)))) - (if (cl-notany 'file-exists-p tag-files) - (message "Error: No tag file found.\ -Create with etags shell command, or visit with `find-tag' or `visit-tags-table'.") - (cl-loop for k being the hash-keys of helm-etags-cache - unless (member k tag-files) - do (remhash k helm-etags-cache)) - (mapc (lambda (f) - (when (or (equal reinit '(4)) - (and helm-etags-mtime-alist - (helm-etags-file-modified-p f))) - (remhash f helm-etags-cache))) - tag-files) - (unless helm-source-etags-select - (setq helm-source-etags-select - (helm-etags-build-source))) - (helm :sources 'helm-source-etags-select - :keymap helm-etags-map - :default (and (stringp str) - (if (or helm-etags-fuzzy-match - (and (eq major-mode 'haskell-mode) - (string-match "[']\\'" str))) - str - (list (concat "\\_<" str "\\_>") str))) - :buffer "*helm etags*")))) - -(provide 'helm-tags) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-tags.el ends here diff --git a/elpa/helm-20191031.725/helm-types.el b/elpa/helm-20191031.725/helm-types.el deleted file mode 100644 index 868e7974..00000000 --- a/elpa/helm-20191031.725/helm-types.el +++ /dev/null @@ -1,322 +0,0 @@ -;;; helm-types.el --- Helm types classes and methods. -*- lexical-binding: t -*- - -;; Copyright (C) 2015 ~ 2019 Thierry Volpiatto - -;; Author: Thierry Volpiatto -;; URL: http://github.com/emacs-helm/helm - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - - -;;; Code: - -(require 'cl-lib) -(require 'eieio) - - -;; Files -(defclass helm-type-file (helm-source) () - "A class to define helm type file.") - -(defmethod helm-source-get-action-from-type ((object helm-type-file)) - (slot-value object 'action)) - -(defun helm-actions-from-type-file () - (let ((source (make-instance 'helm-type-file))) - (helm--setup-source source) - (helm-source-get-action-from-type source))) - -(defvar helm-generic-files-map - (let ((map (make-sparse-keymap))) - (set-keymap-parent map helm-map) - (define-key map (kbd "C-]") 'helm-ff-run-toggle-basename) - (define-key map (kbd "C-s") 'helm-ff-run-grep) - (define-key map (kbd "M-g s") 'helm-ff-run-grep) - (define-key map (kbd "M-g z") 'helm-ff-run-zgrep) - (define-key map (kbd "M-g p") 'helm-ff-run-pdfgrep) - (define-key map (kbd "C-c g") 'helm-ff-run-gid) - (define-key map (kbd "M-R") 'helm-ff-run-rename-file) - (define-key map (kbd "M-C") 'helm-ff-run-copy-file) - (define-key map (kbd "M-B") 'helm-ff-run-byte-compile-file) - (define-key map (kbd "M-L") 'helm-ff-run-load-file) - (define-key map (kbd "M-S") 'helm-ff-run-symlink-file) - (define-key map (kbd "M-H") 'helm-ff-run-hardlink-file) - (define-key map (kbd "M-D") 'helm-ff-run-delete-file) - (define-key map (kbd "C-=") 'helm-ff-run-ediff-file) - (define-key map (kbd "C-c =") 'helm-ff-run-ediff-merge-file) - (define-key map (kbd "C-c o") 'helm-ff-run-switch-other-window) - (define-key map (kbd "C-c r") 'helm-ff-run-find-file-as-root) - (define-key map (kbd "C-c C-o") 'helm-ff-run-switch-other-frame) - (define-key map (kbd "M-i") 'helm-ff-properties-persistent) - (define-key map (kbd "C-c C-x") 'helm-ff-run-open-file-externally) - (define-key map (kbd "C-c X") 'helm-ff-run-open-file-with-default-tool) - (define-key map (kbd "M-.") 'helm-ff-run-etags) - (define-key map (kbd "C-c @") 'helm-ff-run-insert-org-link) - (define-key map (kbd "C-x C-q") 'helm-ff-run-marked-files-in-dired) - (define-key map (kbd "C-c C-a") 'helm-ff-run-mail-attach-files) - map) - "Generic Keymap for files.") - -(defcustom helm-type-file-actions - (helm-make-actions - "Find file" 'helm-find-many-files - "Find file as root" 'helm-find-file-as-root - "Find file other window" 'helm-find-files-other-window - "Find file other frame" 'find-file-other-frame - "Open dired in file's directory" 'helm-open-dired - "Attach file(s) to mail buffer `C-c C-a'" 'helm-ff-mail-attach-files - "Marked files in dired" 'helm-marked-files-in-dired - "Grep File(s) `C-u recurse'" 'helm-find-files-grep - "Zgrep File(s) `C-u Recurse'" 'helm-ff-zgrep - "Pdfgrep File(s)" 'helm-ff-pdfgrep - "Insert as org link" 'helm-files-insert-as-org-link - "Checksum File" 'helm-ff-checksum - "Ediff File" 'helm-find-files-ediff-files - "Ediff Merge File" 'helm-find-files-ediff-merge-files - "Etags `M-., C-u reload tag file'" 'helm-ff-etags-select - "View file" 'view-file - "Insert file" 'insert-file - "Add marked files to file-cache" 'helm-ff-cache-add-file - "Delete file(s)" 'helm-ff-delete-files - "Copy file(s) `M-C, C-u to follow'" 'helm-find-files-copy - "Rename file(s) `M-R, C-u to follow'" 'helm-find-files-rename - "Symlink files(s) `M-S, C-u to follow'" 'helm-find-files-symlink - "Relsymlink file(s) `C-u to follow'" 'helm-find-files-relsymlink - "Hardlink file(s) `M-H, C-u to follow'" 'helm-find-files-hardlink - "Open file externally (C-u to choose)" 'helm-open-file-externally - "Open file with default tool" 'helm-open-file-with-default-tool - "Find file in hex dump" 'hexl-find-file) - "Default actions for type files." - :group 'helm-files - :type '(alist :key-type string :value-type function)) - -(defmethod helm--setup-source :primary ((_source helm-type-file))) - -(defmethod helm--setup-source :before ((source helm-type-file)) - (setf (slot-value source 'action) 'helm-type-file-actions) - (setf (slot-value source 'persistent-help) "Show this file") - (setf (slot-value source 'action-transformer) - '(helm-transform-file-load-el - helm-transform-file-browse-url - helm-transform-file-cache)) - (setf (slot-value source 'candidate-transformer) - '(helm-skip-boring-files - helm-w32-pathname-transformer)) - (setf (slot-value source 'filtered-candidate-transformer) - 'helm-highlight-files) - (setf (slot-value source 'help-message) 'helm-generic-file-help-message) - (setf (slot-value source 'mode-line) (list "File(s)" helm-mode-line-string)) - (setf (slot-value source 'keymap) helm-generic-files-map) - (setf (slot-value source 'group) 'helm-files)) - - -;; Bookmarks -(defclass helm-type-bookmark (helm-source) () - "A class to define type bookmarks.") - -(defcustom helm-type-bookmark-actions - (helm-make-actions - "Jump to bookmark" 'helm-bookmark-jump - "Jump to BM other window" 'helm-bookmark-jump-other-window - "Jump to BM other frame" 'helm-bookmark-jump-other-frame - "Bookmark edit annotation" 'bookmark-edit-annotation - "Bookmark show annotation" 'bookmark-show-annotation - "Delete bookmark(s)" 'helm-delete-marked-bookmarks - "Edit Bookmark" 'helm-bookmark-edit-bookmark - "Rename bookmark" 'helm-bookmark-rename - "Relocate bookmark" 'bookmark-relocate) - "Default actions for type bookmarks." - :group 'helm-bookmark - :type '(alist :key-type string - :value-type function)) - -(defmethod helm-source-get-action-from-type ((object helm-type-bookmark)) - (slot-value object 'action)) - -(defmethod helm--setup-source :primary ((_source helm-type-bookmark))) - -(defmethod helm--setup-source :before ((source helm-type-bookmark)) - (setf (slot-value source 'action) 'helm-type-bookmark-actions) - (setf (slot-value source 'keymap) helm-bookmark-map) - (setf (slot-value source 'mode-line) (list "Bookmark(s)" helm-mode-line-string)) - (setf (slot-value source 'help-message) 'helm-bookmark-help-message) - (setf (slot-value source 'migemo) t) - (setf (slot-value source 'follow) 'never) - (setf (slot-value source 'group) 'helm-bookmark)) - - -;; Buffers -(defclass helm-type-buffer (helm-source) () - "A class to define type buffer.") - -(defcustom helm-type-buffer-actions - (helm-make-actions - "Switch to buffer(s)" 'helm-buffer-switch-buffers - "Switch to buffer(s) other window `C-c o'" - 'helm-buffer-switch-buffers-other-window - "Switch to buffer other frame `C-c C-o'" - 'switch-to-buffer-other-frame - (lambda () (and (fboundp 'tab-bar-mode) - "Switch to buffer other tab `C-c C-t'")) - 'switch-to-buffer-other-tab - "Browse project `C-x C-d'" - 'helm-buffers-browse-project - "Query replace regexp `C-M-%'" - 'helm-buffer-query-replace-regexp - "Query replace `M-%'" 'helm-buffer-query-replace - "View buffer" 'view-buffer - "Display buffer" 'display-buffer - "Rename buffer `M-R'" 'helm-buffers-rename-buffer - "Grep buffer(s) `M-g s' (C-u grep all buffers)" - 'helm-zgrep-buffers - "Multi occur buffer(s) `C-s (C-u search also in current)'" - 'helm-multi-occur-as-action - "Revert buffer(s) `M-G'" 'helm-revert-marked-buffers - "Insert buffer" 'insert-buffer - "Kill buffer(s) `M-D'" 'helm-kill-marked-buffers - "Diff with file `C-='" 'diff-buffer-with-file - "Ediff Marked buffers `C-c ='" 'helm-ediff-marked-buffers - "Ediff Merge marked buffers `M-='" - (lambda (candidate) - (helm-ediff-marked-buffers candidate t))) - "Default actions for type buffers." - :group 'helm-buffers - :type '(alist :key-type string :value-type function)) - -(defmethod helm-source-get-action-from-type ((object helm-type-buffer)) - (slot-value object 'action)) - -(defmethod helm--setup-source :primary ((_source helm-type-buffer))) - -(defmethod helm--setup-source :before ((source helm-type-buffer)) - (setf (slot-value source 'action) 'helm-type-buffer-actions) - (setf (slot-value source 'persistent-help) "Show this buffer") - (setf (slot-value source 'mode-line) (list "Buffer(s)" helm-mode-line-string)) - (setf (slot-value source 'filtered-candidate-transformer) - '(helm-skip-boring-buffers - helm-buffers-sort-transformer - helm-highlight-buffers)) - (setf (slot-value source 'group) 'helm-buffers)) - -;; Functions -(defclass helm-type-function (helm-source) () - "A class to define helm type function.") - -(defcustom helm-type-function-actions - (helm-make-actions - "Describe command" 'describe-function - "Add command to kill ring" 'helm-kill-new - "Go to command's definition" 'find-function - "Debug on entry" 'debug-on-entry - "Cancel debug on entry" 'cancel-debug-on-entry - "Trace function" 'trace-function - "Trace function (background)" 'trace-function-background - "Untrace function" 'untrace-function) - "Default actions for type functions." - :group 'helm-elisp - :type '(alist :key-type string :value-type function)) - -(defmethod helm-source-get-action-from-type ((object helm-type-function)) - (slot-value object 'action)) - -(defun helm-actions-from-type-function () - (let ((source (make-instance 'helm-type-function))) - (helm--setup-source source) - (helm-source-get-action-from-type source))) - -(defmethod helm--setup-source :primary ((_source helm-type-function))) - -(defmethod helm--setup-source :before ((source helm-type-function)) - (setf (slot-value source 'action) 'helm-type-function-actions) - (setf (slot-value source 'action-transformer) - 'helm-transform-function-call-interactively) - (setf (slot-value source 'candidate-transformer) - 'helm-mark-interactive-functions) - (setf (slot-value source 'coerce) 'helm-symbolify)) - - -;; Commands -(defclass helm-type-command (helm-source) () - "A class to define helm type command.") - -(defun helm-actions-from-type-command () - (let ((source (make-instance 'helm-type-command))) - (helm--setup-source source) - (helm-source-get-action-from-type source))) - -(defcustom helm-type-command-actions - (append (helm-make-actions - "Call interactively" 'helm-call-interactively) - (helm-actions-from-type-function)) - "Default actions for type command." - :group 'helm-command - :type '(alist :key-type string :value-type function)) - -(defmethod helm--setup-source :primary ((_source helm-type-command))) - -(defmethod helm--setup-source :before ((source helm-type-command)) - (setf (slot-value source 'action) 'helm-type-command-actions) - (setf (slot-value source 'coerce) 'helm-symbolify) - (setf (slot-value source 'persistent-action) 'describe-function) - (setf (slot-value source 'group) 'helm-command)) - -;; Timers -(defclass helm-type-timers (helm-source) () - "A class to define helm type timers.") - -(defcustom helm-type-timers-actions - '(("Cancel Timer" . (lambda (_timer) - (let ((mkd (helm-marked-candidates))) - (cl-loop for timer in mkd - do (cancel-timer timer))))) - ("Describe Function" . (lambda (tm) - (describe-function (timer--function tm)))) - ("Find Function" . (lambda (tm) - (helm-aif (timer--function tm) - (if (byte-code-function-p it) - (message "Can't find anonymous function `%s'" it) - (find-function it)))))) - "Default actions for type timers." - :group 'helm-elisp - :type '(alist :key-type string :value-type function)) - -(defmethod helm--setup-source :primary ((_source helm-type-timers))) - -(defmethod helm--setup-source :before ((source helm-type-timers)) - (setf (slot-value source 'action) 'helm-type-timers-actions) - (setf (slot-value source 'persistent-action) - (lambda (tm) - (describe-function (timer--function tm)))) - (setf (slot-value source 'persistent-help) "Describe Function") - (setf (slot-value source 'group) 'helm-elisp)) - -;; Builders. -(defun helm-build-type-file () - (helm-make-type 'helm-type-file)) - -(defun helm-build-type-function () - (helm-make-type 'helm-type-function)) - -(defun helm-build-type-command () - (helm-make-type 'helm-type-command)) - -(provide 'helm-types) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-types.el ends here diff --git a/elpa/helm-20191031.725/helm-utils.el b/elpa/helm-20191031.725/helm-utils.el deleted file mode 100644 index 7593ecd5..00000000 --- a/elpa/helm-20191031.725/helm-utils.el +++ /dev/null @@ -1,1067 +0,0 @@ -;;; helm-utils.el --- Utilities Functions for helm. -*- lexical-binding: t -*- - -;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto - -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'cl-lib) -(require 'helm) -(require 'helm-help) -(eval-when-compile (require 'dired)) - -(declare-function helm-find-files-1 "helm-files.el" (fname &optional preselect)) -(declare-function popup-tip "ext:popup") -(declare-function markdown-show-subtree "outline.el") -(declare-function outline-show-subtree "outline.el") -(declare-function org-reveal "org.el") -(declare-function tab-bar-tabs "tab-bar.el") -(declare-function tab-bar-select-tab "tab-bar.el") -(defvar org-directory) -(defvar winner-boring-buffers) -(defvar helm-show-completion-overlay) - - -(defgroup helm-utils nil - "Utilities routines for Helm." - :group 'helm) - -(defcustom helm-su-or-sudo "sudo" - "What command to use for root access." - :type 'string - :group 'helm-utils) - -(defcustom helm-default-kbsize 1024.0 - "Default Kbsize to use for showing files size. -It is a float, usually 1024.0 but could be 1000.0 on some systems." - :group 'helm-utils - :type 'float) - -(define-obsolete-variable-alias - 'helm-highlight-number-lines-around-point - 'helm-highlight-matches-around-point-max-lines - "20160119") - -(defcustom helm-highlight-matches-around-point-max-lines 15 - "Number of lines around point where matched items are highlighted." - :group 'helm-utils - :type 'integer) - -(defcustom helm-buffers-to-resize-on-pa nil - "A list of helm buffers where the helm-window should be reduced on persistent actions." - :group 'helm-utils - :type '(repeat (choice string))) - -(defcustom helm-resize-on-pa-text-height 12 - "The size of the helm-window when resizing on persistent action." - :group 'helm-utils - :type 'integer) - -(defcustom helm-sources-using-help-echo-popup '("Moccur" "Imenu in all buffers" - "Ack-Grep" "AG" "RG" "Gid" "Git-Grep") - "Show the buffer name or the filename in a popup at selection." - :group 'helm-utils - :type '(repeat (choice string))) - -(defcustom helm-html-decode-entities-function #'helm-html-decode-entities-string - "Function used to decode html entities in html bookmarks. -Helm comes by default with `helm-html-decode-entities-string', if you need something -more sophisticated you can use `w3m-decode-entities-string' if available. - -In emacs itself org-entities seems broken and `xml-substitute-numeric-entities' -supports only numeric entities." - :group 'helm-utils - :type 'function) - - -(defvar helm-goto-line-before-hook '(helm-save-current-pos-to-mark-ring) - "Run before jumping to line. -This hook run when jumping from `helm-goto-line', `helm-etags-default-action', -and `helm-imenu-default-action'. -This allow you to retrieve a previous position after using the different helm -tools for searching (etags, grep, gid, (m)occur etc...). -By default positions are added to `mark-ring' you can also add to register -by using instead (or adding) `helm-save-pos-to-register-before-jump'. -In this case last position is added to the register -`helm-save-pos-before-jump-register'.") - -(defvar helm-save-pos-before-jump-register ?_ - "The register where `helm-save-pos-to-register-before-jump' save position.") - -(defconst helm-html-entities-alist - '((""" . 34) ;; " - (">" . 62) ;; > - ("<" . 60) ;; < - ("&" . 38) ;; & - ("€" . 8364) ;; € - ("Ÿ" . 89) ;; Y - ("¡" . 161) ;; ¡ - ("¢" . 162) ;; ¢ - ("£" . 163) ;; £ - ("¤" . 164) ;; ¤ - ("¥" . 165) ;; Â¥ - ("¦" . 166) ;; ¦ - ("§" . 167) ;; § - ("¨" . 32) ;; SPC - ("©" . 169) ;; © - ("ª" . 97) ;; a - ("«" . 171) ;; « - ("¬" . 172) ;; ¬ - ("&masr;" . 174) ;; ® - ("°" . 176) ;; ° - ("±" . 177) ;; ± - ("²" . 50) ;; 2 - ("³" . 51) ;; 3 - ("´" . 39) ;; ' - ("µ" . 956) ;; μ - ("¶" . 182) ;; ¶ - ("·" . 183) ;; · - ("¸" . 32) ;; SPC - ("¹" . 49) ;; 1 - ("º" . 111) ;; o - ("»" . 187) ;; » - ("¼" . 49) ;; 1 - ("½" . 49) ;; 1 - ("¾" . 51) ;; 3 - ("¿" . 191) ;; ¿ - ("À" . 192) ;; À - ("Á" . 193) ;; Á - ("Â" . 194) ;;  - ("Ã" . 195) ;; à - ("Ä" . 196) ;; Ä - ("Å" . 197) ;; Å - ("&Aelig" . 198) ;; Æ - ("Ç" . 199) ;; Ç - ("È" . 200) ;; È - ("É" . 201) ;; É - ("Ê" . 202) ;; Ê - ("Ë" . 203) ;; Ë - ("Ì" . 204) ;; Ì - ("Í" . 205) ;; Í - ("Î" . 206) ;; Î - ("Ï" . 207) ;; Ï - ("ð" . 208) ;; Ð - ("Ñ" . 209) ;; Ñ - ("Ò" . 210) ;; Ò - ("Ó" . 211) ;; Ó - ("Ô" . 212) ;; Ô - ("Õ" . 213) ;; Õ - ("Ö" . 214) ;; Ö - ("×" . 215) ;; × - ("Ø" . 216) ;; Ø - ("Ù" . 217) ;; Ù - ("Ú" . 218) ;; Ú - ("Û" . 219) ;; Û - ("Ü" . 220) ;; Ü - ("Ý" . 221) ;; Ý - ("þ" . 222) ;; Þ - ("ß" . 223) ;; ß - ("à" . 224) ;; à - ("á" . 225) ;; á - ("â" . 226) ;; â - ("ã" . 227) ;; ã - ("ä" . 228) ;; ä - ("å" . 229) ;; Ã¥ - ("æ" . 230) ;; æ - ("ç" . 231) ;; ç - ("è" . 232) ;; è - ("é" . 233) ;; é - ("ê" . 234) ;; ê - ("ë" . 235) ;; ë - ("ì" . 236) ;; ì - ("í" . 237) ;; í - ("î" . 238) ;; î - ("ï" . 239) ;; ï - ("ð" . 240) ;; ð - ("ñ" . 241) ;; ñ - ("ò" . 242) ;; ò - ("ó" . 243) ;; ó - ("ô" . 244) ;; ô - ("õ" . 245) ;; õ - ("ö" . 246) ;; ö - ("÷" . 247) ;; ÷ - ("ø" . 248) ;; ø - ("ù" . 249) ;; ù - ("ú" . 250) ;; ú - ("û" . 251) ;; û - ("ü" . 252) ;; ü - ("ý" . 253) ;; ý - ("þ" . 254) ;; þ - ("ÿ" . 255) ;; ÿ - ("®" . 174) ;; ® - ("­" . 173)) ;; ­ - - "Table of html character entities and values.") - -(defvar helm-find-many-files-after-hook nil - "Hook that run at end of `helm-find-many-files'.") - -;;; Faces. -;; -(defface helm-selection-line - '((t (:inherit highlight :distant-foreground "black"))) - "Face used in the `helm-current-buffer' when jumping to candidate." - :group 'helm-faces) - -(defface helm-match-item - '((t (:inherit isearch))) - "Face used to highlight item matched in a selected line." - :group 'helm-faces) - - -;;; Utils functions -;; -;; -(defcustom helm-window-prefer-horizontal-split nil - "Maybe switch to other window vertically when non nil. - -Possible values are t, nil and `decide'. - -When t switch vertically. -When nil switch horizontally. -When `decide' try to guess if it is possible to switch vertically -according to the setting of `split-width-threshold' and the size of -the window from where splitting is done. - -Note that when using `decide' and `split-width-threshold' is nil, the -behavior is the same that with a nil value." - :group 'helm-utils - :type '(choice - (const :tag "Split window vertically" t) - (const :tag "Split window horizontally" nil) - (symbol :tag "Guess how to split window" 'decide))) - -(defcustom helm-window-show-buffers-function #'helm-window-default-split-fn - "The default function to use when opening several buffers at once. -It is typically used to rearrange windows." - :group 'helm-utils - :type '(choice - (function :tag "Split windows vertically or horizontally" - helm-window-default-split-fn) - (function :tag "Split in alternate windows" - helm-window-alternate-split-fn) - (function :tag "Split windows in mosaic" - helm-window-mosaic-fn))) - -(defun helm-window-show-buffers (buffers &optional other-window) - "Show BUFFERS. - -If more than one buffer marked switch to these buffers in separate windows. -If OTHER-WINDOW is non-nil, keep current buffer and switch to others buffers -in separate windows. -If a prefix arg is given split windows vertically." - (let ((initial-ow-fn (if (cdr (window-list)) - #'switch-to-buffer-other-window - #'helm-window-other-window))) - (if (cdr buffers) - (funcall helm-window-show-buffers-function buffers - (and other-window initial-ow-fn)) - (if other-window - (funcall initial-ow-fn (car buffers)) - (helm-buffers-switch-to-buffer-or-tab (car buffers)))))) - -(defun helm-buffers-switch-to-buffer-or-tab (buffer) - "Switch to BUFFER in its tab if some." - (if (and (fboundp 'tab-bar-mode) - helm-buffers-maybe-switch-to-tab) - (let* ((tabs (tab-bar-tabs)) - (tab-names (mapcar (lambda (tab) - (cdr (assq 'name tab))) - (tab-bar-tabs))) - (bname (buffer-name (get-buffer buffer))) - (tab (helm-buffers--get-tab-from-name bname tabs))) - (if (helm-buffers--buffer-in-tab-p bname tab-names) - (progn - (tab-bar-select-tab tab) - (select-window (get-buffer-window bname))) - (switch-to-buffer buffer))) - (switch-to-buffer buffer))) - -(defun helm-buffers--get-tab-from-name (tab-name tabs) - "Return tab from TABS when it contains TAB-NAME." - (cl-loop for tab in tabs - when (member tab-name (split-string (cdr (assq 'name tab)) ", " t)) - return tab)) - -(defun helm-buffers--buffer-in-tab-p (buffer-name tab-names) - "Check if BUFFER-NAME is in TAB-NAMES list." - (cl-loop for name in tab-names - ;; Buf names are separated with "," in TAB-NAMES - ;; e.g. '("tab-bar.el" "*scratch*, helm-buffers.el"). - thereis (member buffer-name (split-string name ", " t)))) - -(defun helm-window-default-split-fn (candidates &optional other-window-fn) - "Split windows in one direction and balance them. - -Direction can be controlled via `helm-window-prefer-horizontal-split'. -If a prefix arg is given split windows the other direction. -This function is suitable for `helm-window-show-buffers-function'." - (if other-window-fn - (funcall other-window-fn (car candidates)) - (switch-to-buffer (car candidates))) - (save-selected-window - (cl-loop with nosplit - for b in (cdr candidates) - when nosplit return - (message "Too many buffers to visit simultaneously") - do (condition-case _err - (helm-window-other-window b 'balance) - (error (setq nosplit t) nil))))) - -(defun helm-window-alternate-split-fn (candidates &optional other-window-fn) - "Split windows horizontally and vertically in alternate fashion. - -Direction can be controlled via `helm-window-prefer-horizontal-split'. -If a prefix arg is given split windows the other direction. -This function is suitable for `helm-window-show-buffers-function'." - (if other-window-fn - (funcall other-window-fn (car candidates)) - (switch-to-buffer (car candidates))) - (let (right-side) - (save-selected-window - (cl-loop with nosplit - for b in (cdr candidates) - when nosplit return - (message "Too many buffers to visit simultaneously") - do (condition-case _err - (let ((helm-current-prefix-arg right-side)) - (helm-window-other-window b) - (setq right-side (not right-side))) - (error (setq nosplit t) nil)))))) - -(defun helm-window-mosaic-fn (candidates &optional other-window-fn) - "Make an as-square-as-possible window mosaic of the CANDIDATES buffers. - -If rectangular, the long side is in the direction given by -`helm-window-prefer-horizontal-split': if non-nil, it is horizontal, vertical -otherwise. -If OTHER-WINDOW-FN is non-nil, current windows are included in the mosaic. -This function is suitable for `helm-window-show-buffers-function'." - (when other-window-fn - (setq candidates (append (mapcar 'window-buffer (window-list)) candidates))) - (delete-other-windows) - (let* ((helm-window-prefer-horizontal-split - (if (eq helm-window-prefer-horizontal-split 'decide) - (and (numberp split-width-threshold) - (>= (window-width (selected-window)) - split-width-threshold)) - helm-window-prefer-horizontal-split)) - mosaic-length-tile-count - mosaic-width-tile-count - mosaic-length-tile-size - mosaic-width-tile-size - next-window) - ;; If 4 tiles, make 2x2 mosaic. - ;; If 5-6 tiles, make 2x3 mosaic with direction depending on `helm-window-prefer-horizontal-split'. - ;; If 7-9 tiles, make 3x3 mosaic. And so on. - (setq mosaic-length-tile-count (ceiling (sqrt (length candidates)))) - (setq mosaic-width-tile-count - (if (<= (length candidates) (* mosaic-length-tile-count (1- mosaic-length-tile-count))) - (1- mosaic-length-tile-count) - mosaic-length-tile-count)) - ;; We lower-bound the tile size, otherwise the function would - ;; fail during the first inner split. - ;; There is consequently no need to check for errors when - ;; splitting. - (let ((frame-mosaic-length-direction-size (frame-height)) - (frame-mosaic-width-direction-size (frame-width)) - (window-mosaic-length-direction-min-size window-min-height) - (window-mosaic-width-direction-min-size window-min-width)) - (if helm-window-prefer-horizontal-split - (setq frame-mosaic-length-direction-size (frame-width) - frame-mosaic-width-direction-size (frame-height) - window-mosaic-length-direction-min-size window-min-width - window-mosaic-width-direction-min-size window-min-height)) - (setq mosaic-length-tile-size (max - (/ frame-mosaic-length-direction-size mosaic-length-tile-count) - window-mosaic-length-direction-min-size) - mosaic-width-tile-size (max - (/ frame-mosaic-width-direction-size mosaic-width-tile-count) - window-mosaic-width-direction-min-size)) - ;; Shorten `candidates' to `max-tiles' elements. - (let ((max-tiles (* (/ frame-mosaic-length-direction-size mosaic-length-tile-size) - (/ frame-mosaic-width-direction-size mosaic-width-tile-size)))) - (when (> (length candidates) max-tiles) - (message "Too many buffers to visit simultaneously") - (setcdr (nthcdr (- max-tiles 1) candidates) nil)))) - ;; Make the mosaic. - (while candidates - (when (> (length candidates) mosaic-length-tile-count) - (setq next-window (split-window nil - mosaic-width-tile-size - (not helm-window-prefer-horizontal-split)))) - (switch-to-buffer (pop candidates)) - (dotimes (_ (min (1- mosaic-length-tile-count) (length candidates))) - (select-window (split-window nil - mosaic-length-tile-size - helm-window-prefer-horizontal-split)) - (switch-to-buffer (pop candidates))) - (when next-window - (select-window next-window))))) - -(defun helm-window-other-window (buffer-or-name &optional balance) - "Switch to BUFFER-OR-NAME in other window. -Direction can be controlled via `helm-window-prefer-horizontal-split'. -If a prefix arg is given split windows the other direction. -When argument BALANCE is provided `balance-windows'." - (let* ((helm-window-prefer-horizontal-split - (if (eq helm-window-prefer-horizontal-split 'decide) - (and (numberp split-width-threshold) - (>= (window-width (selected-window)) - split-width-threshold)) - helm-window-prefer-horizontal-split)) - (right-side (if helm-window-prefer-horizontal-split - (not helm-current-prefix-arg) - helm-current-prefix-arg))) - (select-window (split-window nil nil right-side)) - (and balance (balance-windows)) - (switch-to-buffer buffer-or-name))) - -(cl-defun helm-current-buffer-narrowed-p (&optional - (buffer helm-current-buffer)) - "Check if BUFFER is narrowed. -Default is `helm-current-buffer'." - (with-current-buffer buffer - (let ((beg (point-min)) - (end (point-max)) - (total (buffer-size))) - (or (/= beg 1) (/= end (1+ total)))))) - -(defun helm-goto-char (loc) - "Go to char, revealing if necessary." - (goto-char loc) - (let ((fn (cond ((eq major-mode 'org-mode) - ;; On some old Emacs versions org may not be loaded. - (require 'org) - #'org-reveal) - ((and (boundp 'outline-minor-mode) - outline-minor-mode) - #'outline-show-subtree) - ((and (boundp 'markdown-mode-map) - (derived-mode-p 'markdown-mode)) - #'markdown-show-subtree)))) - ;; outline may fail in some conditions e.g. with markdown enabled - ;; (issue #1919). - (condition-case nil - (and fn (funcall fn)) - (error nil)))) - -(defun helm-goto-line (lineno &optional noanim) - "Goto LINENO opening only outline headline if needed. -Animation is used unless NOANIM is non--nil." - (helm-log-run-hook 'helm-goto-line-before-hook) - (helm-match-line-cleanup) - (unless helm-alive-p - (with-helm-current-buffer - (unless helm-yank-point (setq helm-yank-point (point))))) - (goto-char (point-min)) - (helm-goto-char (point-at-bol lineno)) - (unless noanim - (helm-highlight-current-line))) - -(defun helm-save-pos-to-register-before-jump () - "Save current buffer position to `helm-save-pos-before-jump-register'. -To use this add it to `helm-goto-line-before-hook'." - (with-helm-current-buffer - (unless helm-in-persistent-action - (point-to-register helm-save-pos-before-jump-register)))) - -(defun helm-save-current-pos-to-mark-ring () - "Save current buffer position to mark ring. -To use this add it to `helm-goto-line-before-hook'." - (with-helm-current-buffer - (unless helm-in-persistent-action - (set-marker (mark-marker) (point)) - (push-mark (point) 'nomsg)))) - -(defun helm-show-all-candidates-in-source (arg) - "Toggle all or only candidate-number-limit cands in current source. -With a numeric prefix arg show only the ARG number of candidates. -The prefix arg have no effect when toggling to only -candidate-number-limit." - (interactive "p") - (with-helm-alive-p - (with-helm-buffer - (if helm-source-filter - (progn - (setq-local helm-candidate-number-limit - (default-value 'helm-candidate-number-limit)) - (helm-set-source-filter nil)) - (with-helm-default-directory (helm-default-directory) - (setq-local helm-candidate-number-limit (and (> arg 1) arg)) - (helm-set-source-filter - (list (helm-get-current-source)))))))) -(put 'helm-show-all-candidates-in-source 'helm-only t) - -(defun helm-display-all-sources () - "Display all sources previously hidden by `helm-set-source-filter'." - (interactive) - (with-helm-alive-p - (helm-set-source-filter nil))) -(put 'helm-display-all-sources 'helm-only t) - -(defun helm-displaying-source-names () - "Return the list of sources name for this helm session." - (with-current-buffer helm-buffer - (goto-char (point-min)) - (cl-loop with pos - while (setq pos (next-single-property-change (point) 'helm-header)) - do (goto-char pos) - collect (buffer-substring-no-properties (point-at-bol)(point-at-eol)) - do (forward-line 1)))) - -(defun helm-handle-winner-boring-buffers () - "Add `helm-buffer' to `winner-boring-buffers' when quitting/exiting helm. -Add this function to `helm-cleanup-hook' when you don't want to see helm buffers -after running winner-undo/redo." - (require 'winner) - (cl-pushnew helm-buffer winner-boring-buffers :test 'equal)) -(add-hook 'helm-cleanup-hook #'helm-handle-winner-boring-buffers) - -(defun helm-quit-and-find-file () - "Drop into `helm-find-files' from `helm'. -If current selection is a buffer or a file, `helm-find-files' -from its directory." - (interactive) - (with-helm-alive-p - (require 'helm-grep) - (require 'helm-elisp) - (helm-run-after-exit - (lambda (f) - ;; Ensure specifics `helm-execute-action-at-once-if-one' - ;; fns don't run here. - (let (helm-execute-action-at-once-if-one - helm-actions-inherit-frame-settings) ; use this-command - (if (file-exists-p f) - (helm-find-files-1 (file-name-directory f) - (concat - "^" - (regexp-quote - (if helm-ff-transformer-show-only-basename - (helm-basename f) f)))) - (helm-find-files-1 f)))) - (let* ((sel (helm-get-selection)) - (marker (if (consp sel) (markerp (cdr sel)))) - (grep-line (and (stringp sel) - (helm-grep-split-line sel))) - (bmk-name (and (stringp sel) - (not grep-line) - (replace-regexp-in-string "\\`\\*" "" sel))) - (bmk (and bmk-name (assoc bmk-name bookmark-alist))) - (buf (helm-aif (and (bufferp sel) (get-buffer sel)) - (buffer-name it))) - (pkg (and (stringp sel) - (get-text-property 0 'tabulated-list-id sel))) - (default-preselection (or (buffer-file-name helm-current-buffer) - default-directory))) - (cond - ;; Buffer. - (buf (or (buffer-file-name sel) - (car (rassoc buf dired-buffers)) - (and (with-current-buffer buf - (eq major-mode 'org-agenda-mode)) - org-directory - (expand-file-name org-directory)) - (with-current-buffer buf - (expand-file-name default-directory)))) - ;; imenu (marker). - (marker - (or (buffer-file-name (marker-buffer (cdr sel))) - default-preselection)) - ;; Bookmark. - (bmk (helm-aif (bookmark-get-filename bmk) - (if (and helm--url-regexp - (string-match helm--url-regexp it)) - it (expand-file-name it)) - (expand-file-name default-directory))) - ((and (stringp sel) (or (file-remote-p sel) - (file-exists-p sel))) - (expand-file-name sel)) - ;; Grep. - ((and grep-line (file-exists-p (car grep-line))) - (expand-file-name (car grep-line))) - ;; Occur. - (grep-line - (with-current-buffer (get-buffer (car grep-line)) - (expand-file-name (or (buffer-file-name) default-directory)))) - ;; Package (installed). - ((and pkg (package-installed-p pkg)) - (expand-file-name (package-desc-dir pkg))) - ;; Url. - ((and (stringp sel) helm--url-regexp (string-match helm--url-regexp sel)) sel) - ;; Exit brutally from a `with-helm-show-completion' - ((and helm-show-completion-overlay - (overlayp helm-show-completion-overlay)) - (delete-overlay helm-show-completion-overlay) - (remove-hook 'helm-move-selection-after-hook 'helm-show-completion) - (expand-file-name default-preselection)) - ;; Default. - (t (expand-file-name default-preselection))))))) -(put 'helm-quit-and-find-file 'helm-only t) - -(defun helm-generic-sort-fn (s1 s2) - "Sort predicate function for helm candidates. -Args S1 and S2 can be single or \(display . real\) candidates, -that is sorting is done against real value of candidate." - (let* ((qpattern (regexp-quote helm-pattern)) - (reg1 (concat "\\_<" qpattern "\\_>")) - (reg2 (concat "\\_<" qpattern)) - (reg3 helm-pattern) - (split (helm-remove-if-match - "\\`!" (helm-mm-split-pattern helm-pattern))) - (str1 (if (consp s1) (cdr s1) s1)) - (str2 (if (consp s2) (cdr s2) s2)) - (score (lambda (str r1 r2 r3 lst) - (+ (if (string-match (concat "\\`" qpattern) str) 1 0) - (cond ((string-match r1 str) 5) - ((and (string-match " " qpattern) - (string-match - (concat "\\_<" (regexp-quote (car lst))) str) - (cl-loop for r in (cdr lst) - always (string-match r str))) - 4) - ((and (string-match " " qpattern) - (cl-loop for r in lst - always (string-match r str))) - 3) - ((string-match r2 str) 2) - ((string-match r3 str) 1) - (t 0))))) - (sc1 (funcall score str1 reg1 reg2 reg3 split)) - (sc2 (funcall score str2 reg1 reg2 reg3 split))) - (cond ((or (zerop (string-width qpattern)) - (and (zerop sc1) (zerop sc2))) - (string-lessp str1 str2)) - ((= sc1 sc2) - (< (length str1) (length str2))) - (t (> sc1 sc2))))) - -(cl-defun helm-file-human-size (size &optional (kbsize helm-default-kbsize)) - "Return a string showing SIZE of a file in human readable form. -SIZE can be an integer or a float depending it's value. -`file-attributes' will take care of that to avoid overflow error. -KBSIZE is a floating point number, defaulting to `helm-default-kbsize'." - (cl-loop with result = (cons "B" size) - for i in '("k" "M" "G" "T" "P" "E" "Z" "Y") - while (>= (cdr result) kbsize) - do (setq result (cons i (/ (cdr result) kbsize))) - finally return - (helm-acase (car result) - ("B" (format "%s" size)) - (t (format "%.1f%s" (cdr result) it))))) - -(cl-defun helm-file-attributes - (file &key type links uid gid access-time modif-time - status size mode gid-change inode device-num dired human-size - mode-type mode-owner mode-group mode-other (string t)) - "Return `file-attributes' elements of FILE separately according to key value. -Availables keys are: -- TYPE: Same as nth 0 `files-attributes' if STRING is nil - otherwise return either symlink, directory or file (default). -- LINKS: See nth 1 `files-attributes'. -- UID: See nth 2 `files-attributes'. -- GID: See nth 3 `files-attributes'. -- ACCESS-TIME: See nth 4 `files-attributes', however format time - when STRING is non--nil (the default). -- MODIF-TIME: See nth 5 `files-attributes', same as above. -- STATUS: See nth 6 `files-attributes', same as above. -- SIZE: See nth 7 `files-attributes'. -- MODE: See nth 8 `files-attributes'. -- GID-CHANGE: See nth 9 `files-attributes'. -- INODE: See nth 10 `files-attributes'. -- DEVICE-NUM: See nth 11 `files-attributes'. -- DIRED: A line similar to what 'ls -l' return. -- HUMAN-SIZE: The size in human form, see `helm-file-human-size'. -- MODE-TYPE, mode-owner,mode-group, mode-other: Split what - nth 7 `files-attributes' return in four categories. -- STRING: When non--nil (default) `helm-file-attributes' return - more friendly values. -If you want the same behavior as `files-attributes' , -\(but with return values in proplist\) use a nil value for STRING. -However when STRING is non--nil, time and type value are different from what -you have in `file-attributes'." - (helm-aif (file-attributes file string) - (let* ((all (cl-destructuring-bind - (type links uid gid access-time modif-time - status size mode gid-change inode device-num) - it - (list :type (if string - (cond ((stringp type) "symlink") ; fname - (type "directory") ; t - (t "file")) ; nil - type) - :links links - :uid uid - :gid gid - :access-time (if string - (format-time-string - "%Y-%m-%d %R" access-time) - access-time) - :modif-time (if string - (format-time-string - "%Y-%m-%d %R" modif-time) - modif-time) - :status (if string - (format-time-string - "%Y-%m-%d %R" status) - status) - :size size - :mode mode - :gid-change gid-change - :inode inode - :device-num device-num))) - (modes (helm-split-mode-file-attributes (cl-getf all :mode)))) - (cond (type (cl-getf all :type)) - (links (cl-getf all :links)) - (uid (cl-getf all :uid)) - (gid (cl-getf all :gid)) - (access-time (cl-getf all :access-time)) - (modif-time (cl-getf all :modif-time)) - (status (cl-getf all :status)) - (size (cl-getf all :size)) - (mode (cl-getf all :mode)) - (gid-change (cl-getf all :gid-change)) - (inode (cl-getf all :inode)) - (device-num (cl-getf all :device-num)) - (dired (concat - (helm-split-mode-file-attributes - (cl-getf all :mode) t) " " - (number-to-string (cl-getf all :links)) " " - (cl-getf all :uid) ":" - (cl-getf all :gid) " " - (if human-size - (helm-file-human-size (cl-getf all :size)) - (int-to-string (cl-getf all :size))) " " - (cl-getf all :modif-time))) - (human-size (helm-file-human-size (cl-getf all :size))) - (mode-type (cl-getf modes :mode-type)) - (mode-owner (cl-getf modes :user)) - (mode-group (cl-getf modes :group)) - (mode-other (cl-getf modes :other)) - (t (append all modes)))))) - -(defun helm-split-mode-file-attributes (str &optional string) - "Split mode file attributes STR into a proplist. -If STRING is non--nil return instead a space separated string." - (cl-loop with type = (substring str 0 1) - with cdr = (substring str 1) - for i across cdr - for count from 1 - if (<= count 3) - concat (string i) into user - if (and (> count 3) (<= count 6)) - concat (string i) into group - if (and (> count 6) (<= count 9)) - concat (string i) into other - finally return - (if string - (mapconcat 'identity (list type user group other) " ") - (list :mode-type type :user user :group group :other other)))) - -(defun helm-format-columns-of-files (files) - "Same as `dired-format-columns-of-files'. -Inlined here for compatibility." - (let ((beg (point))) - (completion--insert-strings files) - (put-text-property beg (point) 'mouse-face nil))) - -(defmacro with-helm-display-marked-candidates (buffer-or-name candidates &rest body) - (declare (indent 0) (debug t)) - (helm-with-gensyms (buffer window) - `(let* ((,buffer (temp-buffer-window-setup ,buffer-or-name)) - (helm-always-two-windows t) - (helm-split-window-default-side - (if (eq helm-split-window-default-side 'same) - 'below helm-split-window-default-side)) - helm-split-window-inside-p - helm-reuse-last-window-split-state - ,window) - (with-current-buffer ,buffer - (helm-format-columns-of-files ,candidates)) - (unwind-protect - (with-selected-window - (setq ,window (temp-buffer-window-show - ,buffer - '(display-buffer-below-selected - (window-height . fit-window-to-buffer)))) - (progn ,@body)) - (quit-window 'kill ,window))))) - -;;; Persistent Action Helpers -;; -;; -;; Internal -(defvar helm-match-line-overlay nil) -(defvar helm--match-item-overlays nil) - -(defun helm-highlight-current-line (&optional start end buf face) - "Highlight and underline current position" - (let* ((start (or start (line-beginning-position))) - (end (or end (1+ (line-end-position)))) - start-match end-match - (args (list start end buf)) - (case-fold-search (if helm-alive-p - (helm-set-case-fold-search) - case-fold-search))) - ;; Highlight the current line. - (if (not helm-match-line-overlay) - (setq helm-match-line-overlay (apply 'make-overlay args)) - (apply 'move-overlay helm-match-line-overlay args)) - (overlay-put helm-match-line-overlay - 'face (or face 'helm-selection-line)) - ;; Now highlight matches only if we are in helm session, we are - ;; maybe coming from helm-grep-mode or helm-moccur-mode buffers. - (when helm-alive-p - (if (or (null helm-highlight-matches-around-point-max-lines) - (zerop helm-highlight-matches-around-point-max-lines)) - (setq start-match start - end-match end) - (setq start-match - (save-excursion - (forward-line - (- helm-highlight-matches-around-point-max-lines)) - (point-at-bol)) - end-match - (save-excursion - (forward-line - helm-highlight-matches-around-point-max-lines) - (point-at-bol)))) - (catch 'empty-line - (cl-loop with ov - for r in (helm-remove-if-match - "\\`!" (helm-mm-split-pattern - (if (with-helm-buffer - ;; Needed for highlighting AG matches. - (assq 'pcre (helm-get-current-source))) - (helm--translate-pcre-to-elisp helm-input) - helm-input))) - do (save-excursion - (goto-char start-match) - (while (condition-case _err - (if helm-migemo-mode - (helm-mm-migemo-forward r end-match t) - (re-search-forward r end-match t)) - (invalid-regexp nil)) - (let ((s (match-beginning 0)) - (e (match-end 0))) - (if (= s e) - (throw 'empty-line nil) - (push (setq ov (make-overlay s e)) - helm--match-item-overlays) - (overlay-put ov 'face 'helm-match-item) - (overlay-put ov 'priority 1)))))))) - (recenter))) - -(defun helm--translate-pcre-to-elisp (regexp) - "Should translate pcre REGEXP to elisp regexp. -Assume regexp is a pcre based regexp." - (with-temp-buffer - (insert " " regexp " ") - (goto-char (point-min)) - (save-excursion - ;; match (){}| unquoted - (helm-awhile (and (re-search-forward "\\([(){}|]\\)" nil t) - (match-string 1)) - (let ((pos (match-beginning 1))) - (if (eql (char-before pos) ?\\) - (delete-region pos (1- pos)) - (replace-match (concat "\\" it) t t nil 1))))) - ;; match \s or \S - (helm-awhile (and (re-search-forward "\\S\\?\\(\\s\\[sS]\\)[^-]" nil t) - (match-string 1)) - (replace-match (concat it "-") t t nil 1)) - (buffer-substring (1+ (point-min)) (1- (point-max))))) - -(defun helm-match-line-cleanup () - (when helm-match-line-overlay - (delete-overlay helm-match-line-overlay) - (setq helm-match-line-overlay nil)) - (when helm--match-item-overlays - (mapc 'delete-overlay helm--match-item-overlays))) - -(defun helm-match-line-cleanup-maybe () - (when (helm-empty-buffer-p) - (helm-match-line-cleanup))) - -(defun helm-match-line-update () - (when helm-match-line-overlay - (delete-overlay helm-match-line-overlay) - (helm-highlight-current-line))) - -(defun helm-persistent-autoresize-hook () - (when (and helm-buffers-to-resize-on-pa - (member helm-buffer helm-buffers-to-resize-on-pa) - (eq helm-split-window-state 'vertical)) - (set-window-text-height (helm-window) helm-resize-on-pa-text-height))) - -(defun helm-match-line-cleanup-pulse () - (run-with-timer 0.3 nil #'helm-match-line-cleanup)) - -(add-hook 'helm-after-update-hook 'helm-match-line-cleanup-maybe) -(add-hook 'helm-after-persistent-action-hook 'helm-persistent-autoresize-hook) -(add-hook 'helm-cleanup-hook 'helm-match-line-cleanup) -(add-hook 'helm-after-action-hook 'helm-match-line-cleanup-pulse) -(add-hook 'helm-after-persistent-action-hook 'helm-match-line-update) - -;;; Popup buffer-name or filename in grep/moccur/imenu-all. -;; -(defvar helm--show-help-echo-timer nil) - -(defun helm-cancel-help-echo-timer () - (when helm--show-help-echo-timer - (cancel-timer helm--show-help-echo-timer) - (setq helm--show-help-echo-timer nil))) - -(defun helm-maybe-show-help-echo () - (when helm--show-help-echo-timer - (cancel-timer helm--show-help-echo-timer) - (setq helm--show-help-echo-timer nil)) - (when (and helm-alive-p - helm-popup-tip-mode - (member (assoc-default 'name (helm-get-current-source)) - helm-sources-using-help-echo-popup)) - (setq helm--show-help-echo-timer - (run-with-timer - 1 nil - (lambda () - (save-selected-window - (with-helm-window - (helm-aif (get-text-property (point-at-bol) 'help-echo) - (popup-tip (concat " " (abbreviate-file-name - (replace-regexp-in-string "\n.*" "" it))) - :around nil - :point (save-excursion - (end-of-visual-line) (point))))))))))) - -;;;###autoload -(define-minor-mode helm-popup-tip-mode - "Show help-echo informations in a popup tip at end of line." - :global t - (require 'popup) - (if helm-popup-tip-mode - (progn - (add-hook 'helm-move-selection-after-hook 'helm-maybe-show-help-echo) - (add-hook 'helm-cleanup-hook 'helm-cancel-help-echo-timer)) - (remove-hook 'helm-move-selection-after-hook 'helm-maybe-show-help-echo) - (remove-hook 'helm-cleanup-hook 'helm-cancel-help-echo-timer))) - -(defun helm-open-file-with-default-tool (file) - "Open FILE with the default tool on this platform." - (let (process-connection-type) - (if (eq system-type 'windows-nt) - (helm-w32-shell-execute-open-file file) - (start-process "helm-open-file-with-default-tool" - nil - (cond ((eq system-type 'gnu/linux) - "xdg-open") - ((or (eq system-type 'darwin) ;; Mac OS X - (eq system-type 'macos)) ;; Mac OS 9 - "open")) - file)))) - -(defun helm-open-dired (file) - "Opens a dired buffer in FILE's directory. If FILE is a -directory, open this directory." - (if (file-directory-p file) - (dired file) - (dired (file-name-directory file)) - (dired-goto-file file))) - -(defun helm-require-or-error (feature function) - (or (require feature nil t) - (error "Need %s to use `%s'." feature function))) - -(defun helm-find-file-as-root (candidate) - (let* ((buf (helm-basename candidate)) - (host (file-remote-p candidate 'host)) - (remote-path (format "/%s:%s:%s" - helm-su-or-sudo - (or host "") - (expand-file-name - (if host - (file-remote-p candidate 'localname) - candidate)))) - non-essential) - (if (buffer-live-p (get-buffer buf)) - (progn - (set-buffer buf) - (find-alternate-file remote-path)) - (find-file remote-path)))) - -(defun helm-find-many-files (_ignore) - "Simple action that run `find-file' on marked candidates. -Run `helm-find-many-files-after-hook' at end" - (let ((helm--reading-passwd-or-string t)) - (mapc 'find-file (helm-marked-candidates)) - (helm-log-run-hook 'helm-find-many-files-after-hook))) - -(defun helm-read-repeat-string (prompt &optional count) - "Prompt as many time PROMPT is not empty. -If COUNT is non--nil add a number after each prompt." - (cl-loop with elm - while (not (string= elm "")) - for n from 1 - do (when count - (setq prompt (concat prompt (int-to-string n) ": "))) - collect (setq elm (helm-read-string prompt)) into lis - finally return (remove "" lis))) - -(defun helm-html-bookmarks-to-alist (file url-regexp bmk-regexp) - "Parse html bookmark FILE and return an alist with (title . url) as elements." - (let (bookmarks-alist url title) - (with-temp-buffer - (insert-file-contents file) - (goto-char (point-min)) - (while (re-search-forward "href=\\|^ *
- -;; This program is free software; you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;;; Code: - -(require 'helm-for-files) - - -;;; List of files gleaned from every dired buffer -;; -;; -(defun helm-files-in-all-dired-candidates () - (save-excursion - (cl-loop for (f . b) in dired-buffers - when (buffer-live-p b) - append (let ((dir (with-current-buffer b dired-directory))) - (if (listp dir) (cdr dir) - (directory-files f t dired-re-no-dot)))))) - -;; (dired '("~/" "~/.emacs.d/.emacs-custom.el" "~/.emacs.d/.emacs.bmk")) - -(defclass helm-files-dired-source (helm-source-sync helm-type-file) - ((candidates :initform #'helm-files-in-all-dired-candidates))) - -(defvar helm-source-files-in-all-dired - (helm-make-source "Files in all dired buffer." 'helm-files-dired-source)) - -;;; session.el files -;; -;; session (http://emacs-session.sourceforge.net/) is an alternative to -;; recentf that saves recent file history and much more. -(defvar session-file-alist) -(defclass helm-source-session-class (helm-source-sync) - ((candidates :initform (lambda () - (cl-delete-if-not - (lambda (f) - (or (string-match helm-tramp-file-name-regexp f) - (file-exists-p f))) - (mapcar 'car session-file-alist)))) - (keymap :initform helm-generic-files-map) - (help-message :initform helm-generic-file-help-message) - (action :initform 'helm-type-file-actions))) - -(defvar helm-source-session nil - "File list from emacs-session.") - -(defcustom helm-session-fuzzy-match nil - "Enable fuzzy matching in `helm-source-session' when non--nil." - :group 'helm-files - :type 'boolean - :set (lambda (var val) - (set var val) - (setq helm-source-session - (helm-make-source "Session" 'helm-source-session-class - :fuzzy-match val)))) - - -;;; External searching file tools. -;; -;; Tracker desktop search - -(defun helm-source-tracker-transformer (candidates _source) - ;; loop through tracker candidates selecting out file:// lines - ;; then select part after file:// and url decode to get straight filenames - (cl-loop for cand in candidates - when (and (stringp cand) - (string-match "\\`[[:space:]]*file://\\(.*\\)" cand)) - collect (url-unhex-string (match-string 1 cand)))) - -(defvar helm-source-tracker-search - (helm-build-async-source "Tracker Search" - :candidates-process - (lambda () - ;; the tracker-search command has been deprecated, now invoke via tracker - ;; also, disable the contextual snippets which we don't currently use - (start-process "tracker-search-process" nil - "tracker" "search" - "--disable-snippets" - "--disable-color" - "--limit=512" - helm-pattern)) - ;; new simplified transformer of tracker search results - :filtered-candidate-transformer #'helm-source-tracker-transformer - ;;(multiline) ; https://github.com/emacs-helm/helm/issues/529 - :keymap helm-generic-files-map - :action 'helm-type-file-actions - :action-transformer '(helm-transform-file-load-el - helm-transform-file-browse-url) - :requires-pattern 3) - "Source for retrieving files matching the current input pattern -with the tracker desktop search.") - -;; Spotlight (MacOS X desktop search) -(defclass helm-mac-spotlight-source (helm-source-async helm-type-file) - ((candidates-process :initform - (lambda () - (start-process - "mdfind-process" nil "mdfind" helm-pattern))) - (requires-pattern :initform 3))) - -(defvar helm-source-mac-spotlight - (helm-make-source "mdfind" 'helm-mac-spotlight-source) - "Source for retrieving files via Spotlight's command line -utility mdfind.") - -(provide 'helm-x-files) - -;; Local Variables: -;; byte-compile-warnings: (not obsolete) -;; coding: utf-8 -;; indent-tabs-mode: nil -;; End: - -;;; helm-x-files.el ends here diff --git a/elpa/helm-20191031.839/emacs-helm.sh b/elpa/helm-20191031.839/emacs-helm.sh new file mode 100755 index 00000000..848a72c6 --- /dev/null +++ b/elpa/helm-20191031.839/emacs-helm.sh @@ -0,0 +1,219 @@ +#!/usr/bin/env sh + + +## Copyright (C) 2012 ~ 2019 Thierry Volpiatto +## +## This program is free software; you can redistribute it and/or modify +## it under the terms of the GNU General Public License as published by +## the Free Software Foundation, either version 3 of the License, or +## (at your option) any later version. +## +## This program is distributed in the hope that it will be useful, +## but WITHOUT ANY WARRANTY; without even the implied warranty of +## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +## GNU General Public License for more details. +## +## You should have received a copy of the GNU General Public License +## along with this program. If not, see . + +## Commentary: +# Preconfigured `emacs -Q' with a basic Helm configuration. + + +# If TEMP env var exists, use it, otherwise declare it. +test -z "$TEMP" && TEMP="/tmp" + +CONF_FILE="$TEMP/helm-cfg.el" +EMACS=emacs +TOOLBARS=-1 +LOAD_PACKAGES= + +usage () { + cat >&1 < $CONF_FILE <\`helm-find-files'\\n\ +;; - \`occur'(M-s o) =>\`helm-occur'\\n\ +;; - \`list-buffers'(C-x C-b) =>\`helm-buffers-list'\\n\ +;; - \`completion-at-point'(M-tab) =>\`helm-lisp-completion-at-point'[1]\\n\ +;; - \`apropos-command'(C-h a) =>\`helm-apropos'\\n\ +;; - \`dabbrev-expand'(M-/) =>\`helm-dabbrev'\\n\ +;; - \`execute-extended-command'(M-x) =>\`helm-M-x'\\n\\n +;; Some other Emacs commands are \"helmized\" by \`helm-mode'.\\n\ +;; [1] Coming with emacs-24.4, \`completion-at-point' is \"helmized\" by \`helm-mode'\\n\ + +;; which provides Helm completion in many places like \`shell-mode'.\\n\ +;; Find context help for most Helm commands with \`C-h m'.\\n\ +;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;\\n\\n")) + +(setq load-path (quote $LOAD_PATH)) +(require 'package) +;; User may be using a non standard \`package-user-dir'. +;; Modify \`package-directory-list' instead of \`package-user-dir' +;; in case the user starts Helm from a non-ELPA installation. +(unless (file-equal-p package-user-dir "~/.emacs.d/elpa") + (add-to-list 'package-directory-list (directory-file-name + (file-name-directory + (directory-file-name default-directory))))) + +(let* ((str-lst "$LOAD_PACKAGES") + (load-packages (and str-lst + (not (string= str-lst "")) + (split-string str-lst ",")))) + (setq package-load-list + (if (equal load-packages '("all")) + '(all) + (append '((helm-core t) (helm t) (async t) (popup t)) + (mapcar (lambda (p) (list (intern p) t)) load-packages))))) + +(package-initialize) +(add-to-list 'load-path (file-name-directory (file-truename "$0"))) +(unless (> $TOOLBARS 0) + (setq default-frame-alist '((vertical-scroll-bars . nil) + (tool-bar-lines . 0) + (menu-bar-lines . 0) + (fullscreen . nil)))) +(blink-cursor-mode -1) +(require 'helm-config) +(helm-mode 1) +(define-key global-map [remap find-file] 'helm-find-files) +(define-key global-map [remap occur] 'helm-occur) +(define-key global-map [remap list-buffers] 'helm-buffers-list) +(define-key global-map [remap dabbrev-expand] 'helm-dabbrev) +(define-key global-map [remap execute-extended-command] 'helm-M-x) +(define-key global-map [remap apropos-command] 'helm-apropos) +(unless (boundp 'completion-in-region-function) + (define-key lisp-interaction-mode-map [remap completion-at-point] 'helm-lisp-completion-at-point) + (define-key emacs-lisp-mode-map [remap completion-at-point] 'helm-lisp-completion-at-point)) +(add-hook 'kill-emacs-hook #'(lambda () (and (file-exists-p "$CONF_FILE") (delete-file "$CONF_FILE")))) +EOF + +$EMACS -Q -l "$CONF_FILE" "$@" diff --git a/elpa/helm-20191031.839/helm-adaptive.el b/elpa/helm-20191031.839/helm-adaptive.el new file mode 100644 index 00000000..13b6f638 --- /dev/null +++ b/elpa/helm-20191031.839/helm-adaptive.el @@ -0,0 +1,278 @@ +;;; helm-adaptive.el --- Adaptive Sorting of Candidates. -*- lexical-binding: t -*- + +;; Original Author: Tamas Patrovics + +;; Copyright (C) 2007 Tamas Patrovics +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'cl-lib) +(require 'helm) + + +(defgroup helm-adapt nil + "Adaptative sorting of candidates for Helm." + :group 'helm) + +(defcustom helm-adaptive-history-file + "~/.emacs.d/helm-adaptive-history" + "Path of file where history information is stored. +When nil history is not saved nor restored after emacs restart unless +you save/restore `helm-adaptive-history' with something else like +psession or desktop." + :type 'string + :group 'helm-adapt) + +(defcustom helm-adaptive-history-length 50 + "Maximum number of candidates stored for a source." + :type 'number + :group 'helm-adapt) + +(defcustom helm-adaptive-sort-by-frequent-recent-usage t + "Try to sort on an average of frequent and recent usage when non-nil. + +When nil sort on frequency usage only. + +Only frequency: +When candidate have low frequency, you have to hit on it many times to +make it going up on top. + +Frequency+recent: +Even with a low frequency, candidate go up on top. If a candidate +have a high frequency but it is not used since some time, it goes +down slowly, but as soon you reuse it it go up on top quickly." + :group 'helm-adapt + :type 'boolean) + +;; Internal +(defvar helm-adaptive-done nil + "nil if history information is not yet stored for the current +selection.") + +(defvar helm-adaptive-history nil + "Contains the stored history information. +Format: ((SOURCE-NAME (SELECTED-CANDIDATE (PATTERN . NUMBER-OF-USE) ...) ...) ...)") + +(defconst helm-adaptive-freq-coefficient 5) +(defconst helm-adaptive-recent-coefficient 2) + +(defun helm-adaptive-done-reset () + (setq helm-adaptive-done nil)) + +;;;###autoload +(define-minor-mode helm-adaptive-mode + "Toggle adaptive sorting in all sources." + :group 'helm-adapt + :require 'helm-adaptive + :global t + (if helm-adaptive-mode + (progn + (unless helm-adaptive-history + (helm-adaptive-maybe-load-history)) + (add-hook 'kill-emacs-hook 'helm-adaptive-save-history) + ;; Should run at beginning of `helm-initial-setup'. + (add-hook 'helm-before-initialize-hook 'helm-adaptive-done-reset) + ;; Should run at beginning of `helm-exit-minibuffer'. + (add-hook 'helm-before-action-hook 'helm-adaptive-store-selection) + ;; Should run at beginning of `helm-select-action'. + (add-hook 'helm-select-action-hook 'helm-adaptive-store-selection)) + (helm-adaptive-save-history) + (setq helm-adaptive-history nil) + (remove-hook 'kill-emacs-hook 'helm-adaptive-save-history) + (remove-hook 'helm-before-initialize-hook 'helm-adaptive-done-reset) + (remove-hook 'helm-before-action-hook 'helm-adaptive-store-selection) + (remove-hook 'helm-select-action-hook 'helm-adaptive-store-selection))) + +(defun helm-adapt-use-adaptive-p (&optional source-name) + "Return current source only if it use adaptive history, nil otherwise." + (when helm-adaptive-mode + (let* ((source (or source-name (helm-get-current-source))) + (adapt-source (or (assoc-default 'filtered-candidate-transformer source) + (assoc-default 'candidate-transformer source)))) + (if (listp adapt-source) + (and (memq 'helm-adaptive-sort adapt-source) source) + (and (eq adapt-source 'helm-adaptive-sort) source))))) + +(defun helm-adaptive-store-selection () + "Store history information for the selected candidate." + (unless helm-adaptive-done + (setq helm-adaptive-done t) + (let ((source (helm-adapt-use-adaptive-p))) + (when source + (let* ((source-name (assoc-default 'name source)) + (source-info (or (assoc source-name helm-adaptive-history) + (progn + (push (list source-name) helm-adaptive-history) + (car helm-adaptive-history)))) + (selection (helm-get-selection nil t)) + (selection-info (progn + (setcdr source-info + (cons + (let ((found (assoc selection (cdr source-info)))) + (if (not found) + ;; new entry + (list selection) + ;; move entry to the beginning of the + ;; list, so that it doesn't get + ;; trimmed when the history is + ;; truncated + (setcdr source-info + (delete found (cdr source-info))) + found)) + (cdr source-info))) + (cadr source-info))) + (pattern-info (progn + (setcdr selection-info + (cons + (let ((found (assoc helm-pattern (cdr selection-info)))) + (if (not found) + ;; new entry + (cons helm-pattern 0) + ;; move entry to the beginning of the + ;; list, so if two patterns used the + ;; same number of times then the one + ;; used last appears first in the list + (setcdr selection-info + (delete found (cdr selection-info))) + found)) + (cdr selection-info))) + (cadr selection-info))) + (timestamp-info (helm-aif (assq 'timestamp (cdr selection-info)) + it + (setcdr selection-info (cons (cons 'timestamp 0) (cdr selection-info))) + (cadr selection-info)))) + ;; Increase usage count. + (setcdr pattern-info (1+ (cdr pattern-info))) + ;; Update timestamp. + (setcdr timestamp-info (float-time)) + ;; Truncate history if needed. + (if (> (length (cdr selection-info)) helm-adaptive-history-length) + (setcdr selection-info + (cl-subseq (cdr selection-info) 0 helm-adaptive-history-length)))))))) + +(defun helm-adaptive-maybe-load-history () + "Load `helm-adaptive-history-file' which contain `helm-adaptive-history'. +Returns nil if `helm-adaptive-history-file' doesn't exist." + (when (and helm-adaptive-history-file + (file-readable-p helm-adaptive-history-file)) + (load-file helm-adaptive-history-file))) + +(defun helm-adaptive-save-history (&optional arg) + "Save history information to file given by `helm-adaptive-history-file'." + (interactive "p") + (when helm-adaptive-history-file + (with-temp-buffer + (insert + ";; -*- mode: emacs-lisp -*-\n" + ";; History entries used for helm adaptive display.\n") + (let (print-length print-level) + (prin1 `(setq helm-adaptive-history ',helm-adaptive-history) + (current-buffer))) + (insert ?\n) + (write-region (point-min) (point-max) helm-adaptive-history-file nil + (unless arg 'quiet))))) + +(defun helm-adaptive-sort (candidates source) + "Sort the CANDIDATES for SOURCE by usage frequency. +This is a filtered candidate transformer you can use with the +`filtered-candidate-transformer' attribute." + (let* ((source-name (assoc-default 'name source)) + (source-info (assoc source-name helm-adaptive-history))) + (if source-info + (let ((usage + ;; Loop in the SOURCE entry of `helm-adaptive-history' + ;; and assemble a list containing the (CANDIDATE + ;; . USAGE-COUNT) pairs. + (cl-loop with cf = (if helm-adaptive-sort-by-frequent-recent-usage + helm-adaptive-freq-coefficient 1) + with cr = helm-adaptive-recent-coefficient + for (src-cand . infos) in (cdr source-info) + for count-freq = 0 + for count-rec = + (helm-aif (and helm-adaptive-sort-by-frequent-recent-usage + (assq 'timestamp infos)) + (* cr (+ (float-time) (cdr it))) + 0) + do (cl-loop for (pattern . score) in + (remove (assq 'timestamp infos) infos) + ;; If current pattern is equal to + ;; the previously used one then + ;; this candidate has priority + ;; (that's why its count-freq is + ;; boosted by 10000) and it only + ;; has to compete with other + ;; candidates which were also + ;; selected with the same pattern. + if (equal pattern helm-pattern) + return (setq count-freq (+ 10000 score)) + else do (cl-incf count-freq score)) + and collect (cons src-cand (+ (* count-freq cf) count-rec)) + into results + ;; Sort the list in descending order, so + ;; candidates with highest priority come + ;; first. + finally return + (sort results (lambda (first second) + (> (cdr first) (cdr second))))))) + (if (consp usage) + ;; Put those candidates first which have the highest usage count. + (cl-loop for (cand . _freq) in usage + for info = (or (and (assq 'multiline source) + (replace-regexp-in-string + "\n\\'" "" cand)) + cand) + when (cl-member info candidates + :test 'helm-adaptive-compare) + collect (car it) into sorted + and do (setq candidates + (cl-remove info candidates + :test 'helm-adaptive-compare)) + finally return (append sorted candidates)) + (message "Your `%s' is maybe corrupted or too old, \ +you should reinitialize it with `helm-reset-adaptive-history'" + helm-adaptive-history-file) + (sit-for 1) + candidates)) + ;; if there is no information stored for this source then do nothing + candidates))) + +;;;###autoload +(defun helm-reset-adaptive-history () + "Delete all `helm-adaptive-history' and his file. +Useful when you have a old or corrupted `helm-adaptive-history-file'." + (interactive) + (when (y-or-n-p "Really delete all your `helm-adaptive-history'? ") + (setq helm-adaptive-history nil) + (delete-file helm-adaptive-history-file))) + +(defun helm-adaptive-compare (x y) + "Compare display parts if some of candidates X and Y. + +Arguments X and Y are cons cell in (DISPLAY . REAL) format or atoms." + (equal (if (listp x) (car x) x) + (if (listp y) (car y) y))) + + +(provide 'helm-adaptive) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-adaptive.el ends here diff --git a/elpa/helm-20191031.839/helm-autoloads.el b/elpa/helm-20191031.839/helm-autoloads.el new file mode 100644 index 00000000..490aaec7 --- /dev/null +++ b/elpa/helm-20191031.839/helm-autoloads.el @@ -0,0 +1,1050 @@ +;;; helm-autoloads.el --- automatically extracted autoloads +;; +;;; Code: +(add-to-list 'load-path (directory-file-name (or (file-name-directory #$) (car load-path)))) + +;;;### (autoloads nil "helm-adaptive" "helm-adaptive.el" (23995 4638 +;;;;;; 436387 418000)) +;;; Generated autoloads from helm-adaptive.el + +(defvar helm-adaptive-mode nil "\ +Non-nil if Helm-Adaptive mode is enabled. +See the `helm-adaptive-mode' command +for a description of this minor mode. +Setting this variable directly does not take effect; +either customize it (see the info node `Easy Customization') +or call the function `helm-adaptive-mode'.") + +(custom-autoload 'helm-adaptive-mode "helm-adaptive" nil) + +(autoload 'helm-adaptive-mode "helm-adaptive" "\ +Toggle adaptive sorting in all sources. + +\(fn &optional ARG)" t nil) + +(autoload 'helm-reset-adaptive-history "helm-adaptive" "\ +Delete all `helm-adaptive-history' and his file. +Useful when you have a old or corrupted `helm-adaptive-history-file'. + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-bookmark" "helm-bookmark.el" (23995 4638 +;;;;;; 434400 192000)) +;;; Generated autoloads from helm-bookmark.el + +(autoload 'helm-bookmarks "helm-bookmark" "\ +Preconfigured `helm' for bookmarks. + +\(fn)" t nil) + +(autoload 'helm-filtered-bookmarks "helm-bookmark" "\ +Preconfigured helm for bookmarks (filtered by category). +Optional source `helm-source-bookmark-addressbook' is loaded +only if external addressbook-bookmark package is installed. + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-buffers" "helm-buffers.el" (23995 4638 +;;;;;; 464781 494000)) +;;; Generated autoloads from helm-buffers.el + +(autoload 'helm-buffers-list "helm-buffers" "\ +Preconfigured `helm' to list buffers. + +\(fn)" t nil) + +(autoload 'helm-mini "helm-buffers" "\ +Preconfigured `helm' displaying `helm-mini-default-sources'. + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-color" "helm-color.el" (23995 4638 472345 +;;;;;; 343000)) +;;; Generated autoloads from helm-color.el + +(autoload 'helm-colors "helm-color" "\ +Preconfigured `helm' for color. + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-comint" "helm-comint.el" (23995 4638 +;;;;;; 440314 914000)) +;;; Generated autoloads from helm-comint.el + +(autoload 'helm-comint-prompts "helm-comint" "\ +Pre-configured `helm' to browse the prompts of the current comint buffer. + +\(fn)" t nil) + +(autoload 'helm-comint-prompts-all "helm-comint" "\ +Pre-configured `helm' to browse the prompts of all comint sessions. + +\(fn)" t nil) + +(autoload 'helm-comint-input-ring "helm-comint" "\ +Preconfigured `helm' that provide completion of `comint' history. + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-command" "helm-command.el" (23995 4638 +;;;;;; 456078 739000)) +;;; Generated autoloads from helm-command.el + +(autoload 'helm-M-x "helm-command" "\ +Preconfigured `helm' for Emacs commands. +It is `helm' replacement of regular `M-x' `execute-extended-command'. + +Unlike regular `M-x' emacs vanilla `execute-extended-command' command, +the prefix args if needed, can be passed AFTER starting `helm-M-x'. +When a prefix arg is passed BEFORE starting `helm-M-x', the first `C-u' +while in `helm-M-x' session will disable it. + +You can get help on each command by persistent action. + +\(fn ARG &optional COMMAND-NAME)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-config" "helm-config.el" (23995 4638 +;;;;;; 438309 931000)) +;;; Generated autoloads from helm-config.el + +(autoload 'helm-configuration "helm-config" "\ +Customize `helm'. + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-dabbrev" "helm-dabbrev.el" (23995 4638 +;;;;;; 429022 351000)) +;;; Generated autoloads from helm-dabbrev.el + +(autoload 'helm-dabbrev "helm-dabbrev" "\ +Preconfigured helm for dynamic abbreviations. + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-elisp" "helm-elisp.el" (23995 4638 446565 +;;;;;; 209000)) +;;; Generated autoloads from helm-elisp.el + +(autoload 'helm-lisp-completion-at-point "helm-elisp" "\ +Preconfigured helm for lisp symbol completion at point. + +\(fn)" t nil) + +(autoload 'helm-complete-file-name-at-point "helm-elisp" "\ +Preconfigured helm to complete file name at point. + +\(fn &optional FORCE)" t nil) + +(autoload 'helm-lisp-indent "helm-elisp" "\ + + +\(fn)" t nil) + +(autoload 'helm-lisp-completion-or-file-name-at-point "helm-elisp" "\ +Preconfigured helm to complete lisp symbol or filename at point. +Filename completion happen if string start after or between a double quote. + +\(fn)" t nil) + +(autoload 'helm-apropos "helm-elisp" "\ +Preconfigured helm to describe commands, functions, variables and faces. +In non interactives calls DEFAULT argument should be provided as a string, +i.e the `symbol-name' of any existing symbol. + +\(fn DEFAULT)" t nil) + +(autoload 'helm-manage-advice "helm-elisp" "\ +Preconfigured `helm' to disable/enable function advices. + +\(fn)" t nil) + +(autoload 'helm-locate-library "helm-elisp" "\ +Preconfigured helm to locate elisp libraries. + +\(fn)" t nil) + +(autoload 'helm-timers "helm-elisp" "\ +Preconfigured `helm' for timers. + +\(fn)" t nil) + +(autoload 'helm-complex-command-history "helm-elisp" "\ +Preconfigured helm for complex command history. + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-elisp-package" "helm-elisp-package.el" +;;;;;; (23995 4638 431566 749000)) +;;; Generated autoloads from helm-elisp-package.el + +(autoload 'helm-list-elisp-packages "helm-elisp-package" "\ +Preconfigured helm for listing and handling emacs packages. + +\(fn ARG)" t nil) + +(autoload 'helm-list-elisp-packages-no-fetch "helm-elisp-package" "\ +Preconfigured helm for emacs packages. + +Same as `helm-list-elisp-packages' but don't fetch packages on remote. +Called with a prefix ARG always fetch packages on remote. + +\(fn ARG)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-eshell" "helm-eshell.el" (23995 4638 +;;;;;; 452554 924000)) +;;; Generated autoloads from helm-eshell.el + +(autoload 'helm-esh-pcomplete "helm-eshell" "\ +Preconfigured helm to provide helm completion in eshell. + +\(fn)" t nil) + +(autoload 'helm-eshell-history "helm-eshell" "\ +Preconfigured helm for eshell history. + +\(fn)" t nil) + +(autoload 'helm-eshell-prompts "helm-eshell" "\ +Pre-configured `helm' to browse the prompts of the current Eshell. + +\(fn)" t nil) + +(autoload 'helm-eshell-prompts-all "helm-eshell" "\ +Pre-configured `helm' to browse the prompts of all Eshell sessions. + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-eval" "helm-eval.el" (23995 4638 426076 +;;;;;; 258000)) +;;; Generated autoloads from helm-eval.el + +(autoload 'helm-eval-expression "helm-eval" "\ +Preconfigured helm for `helm-source-evaluation-result'. + +\(fn ARG)" t nil) + +(autoload 'helm-eval-expression-with-eldoc "helm-eval" "\ +Preconfigured helm for `helm-source-evaluation-result' with `eldoc' support. + +\(fn)" t nil) + +(autoload 'helm-calcul-expression "helm-eval" "\ +Preconfigured helm for `helm-source-calculation-result'. + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-external" "helm-external.el" (23995 4638 +;;;;;; 463440 442000)) +;;; Generated autoloads from helm-external.el + +(autoload 'helm-run-external-command "helm-external" "\ +Preconfigured `helm' to run External PROGRAM asyncronously from Emacs. +If program is already running exit with error. +You can set your own list of commands with +`helm-external-commands-list'. + +\(fn PROGRAM)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-files" "helm-files.el" (23995 4638 469439 +;;;;;; 798000)) +;;; Generated autoloads from helm-files.el + +(autoload 'helm-projects-history "helm-files" "\ + + +\(fn ARG)" t nil) + +(autoload 'helm-browse-project "helm-files" "\ +Preconfigured helm to browse projects. +Browse files and see status of project with its vcs. +Only HG and GIT are supported for now. +Fall back to `helm-browse-project-find-files' +if current directory is not under control of one of those vcs. +With a prefix ARG browse files recursively, with two prefix ARG +rebuild the cache. +If the current directory is found in the cache, start +`helm-browse-project-find-files' even with no prefix ARG. +NOTE: The prefix ARG have no effect on the VCS controlled directories. + +Needed dependencies for VCS: + +and +. + +\(fn ARG)" t nil) + +(autoload 'helm-find-files "helm-files" "\ +Preconfigured `helm' for helm implementation of `find-file'. +Called with a prefix arg show history if some. +Don't call it from programs, use `helm-find-files-1' instead. +This is the starting point for nearly all actions you can do on files. + +\(fn ARG)" t nil) + +(autoload 'helm-delete-tramp-connection "helm-files" "\ +Allow deleting tramp connection or marked tramp connections at once. + +This replace `tramp-cleanup-connection' which is partially broken in +emacs < to 25.1.50.1 (See Emacs Bug#24432). + +It allows additionally to delete more than one connection at once. + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-find" "helm-find.el" (23995 4638 460542 +;;;;;; 606000)) +;;; Generated autoloads from helm-find.el + +(autoload 'helm-find "helm-find" "\ +Preconfigured `helm' for the find shell command. + +Recursively find files whose names are matched by all specified +globbing PATTERNs under the current directory using the external +program specified in `find-program' (usually \"find\"). Every +input PATTERN is silently wrapped into two stars: *PATTERN*. + +With prefix argument, prompt for a directory to search. + +When user option `helm-findutils-search-full-path' is non-nil, +match against complete paths, otherwise, against file names +without directory part. + +The (possibly empty) list of globbing PATTERNs can be followed by +the separator \"*\" plus any number of additional arguments that +are passed to \"find\" literally. + +\(fn ARG)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-font" "helm-font.el" (23995 4638 439304 +;;;;;; 202000)) +;;; Generated autoloads from helm-font.el + +(autoload 'helm-select-xfont "helm-font" "\ +Preconfigured `helm' to select Xfont. + +\(fn)" t nil) + +(autoload 'helm-ucs "helm-font" "\ +Preconfigured helm for `ucs-names'. + +Called with a prefix arg force reloading cache. + +\(fn ARG)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-for-files" "helm-for-files.el" (23995 +;;;;;; 4638 427050 563000)) +;;; Generated autoloads from helm-for-files.el + +(autoload 'helm-for-files "helm-for-files" "\ +Preconfigured `helm' for opening files. +Run all sources defined in `helm-for-files-preferred-list'. + +\(fn)" t nil) + +(autoload 'helm-multi-files "helm-for-files" "\ +Preconfigured helm like `helm-for-files' but running locate only on demand. + +Allow toggling back and forth from locate to others sources with +`helm-multi-files-toggle-locate-binding' key. +This avoid launching needlessly locate when what you search is already +found. + +\(fn)" t nil) + +(autoload 'helm-recentf "helm-for-files" "\ +Preconfigured `helm' for `recentf'. + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-grep" "helm-grep.el" (23995 4638 437298 +;;;;;; 323000)) +;;; Generated autoloads from helm-grep.el + +(autoload 'helm-goto-precedent-file "helm-grep" "\ +Go to precedent file in helm grep/etags buffers. + +\(fn)" t nil) + +(autoload 'helm-goto-next-file "helm-grep" "\ +Go to precedent file in helm grep/etags buffers. + +\(fn)" t nil) + +(autoload 'helm-do-grep-ag "helm-grep" "\ +Preconfigured helm for grepping with AG in `default-directory'. +With prefix-arg prompt for type if available with your AG version. + +\(fn ARG)" t nil) + +(autoload 'helm-grep-do-git-grep "helm-grep" "\ +Preconfigured helm for git-grepping `default-directory'. +With a prefix arg ARG git-grep the whole repository. + +\(fn ARG)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-help" "helm-help.el" (23995 4638 435455 +;;;;;; 853000)) +;;; Generated autoloads from helm-help.el + +(autoload 'helm-documentation "helm-help" "\ +Preconfigured Helm for Helm documentation. +With a prefix arg refresh the documentation. + +Find here the documentation of all documented sources. + +\(fn)" t nil) + +(defvar helm-comp-read-mode-line "\\C/\\[helm-cr-empty-string]:Empty \\\\[helm-help]:Help \\[helm-select-action]:Act \\[helm-maybe-exit-minibuffer]/f1/f2/f-n:NthAct \\[helm-toggle-suspend-update]:Tog.suspend \\[helm-customize-group]:Conf") + +(defvar helm-read-file-name-mode-line-string "\\\\[helm-help]:Help C/\\[helm-cr-empty-string]:Empty \\\\[helm-select-action]:Act \\[helm-maybe-exit-minibuffer]/f1/f2/f-n:NthAct \\[helm-toggle-suspend-update]:Tog.suspend \\[helm-customize-group]:Conf" "\ +String displayed in mode-line in `helm-source-find-files'.") + +(defvar helm-top-mode-line "\\\\[helm-help]:Help \\\\[helm-select-action]:Act \\[helm-maybe-exit-minibuffer]/f1/f2/f-n:NthAct \\[helm-toggle-suspend-update]:Tog.suspend \\[helm-customize-group]:Conf") + +;;;*** + +;;;### (autoloads nil "helm-id-utils" "helm-id-utils.el" (23995 4638 +;;;;;; 449602 499000)) +;;; Generated autoloads from helm-id-utils.el + +(autoload 'helm-gid "helm-id-utils" "\ +Preconfigured helm for `gid' command line of `ID-Utils'. +Need A database created with the command `mkid' +above `default-directory'. +Need id-utils as dependency which provide `mkid', `gid' etc... +See . + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-imenu" "helm-imenu.el" (23995 4638 441204 +;;;;;; 502000)) +;;; Generated autoloads from helm-imenu.el + +(autoload 'helm-imenu "helm-imenu" "\ +Preconfigured `helm' for `imenu'. + +\(fn)" t nil) + +(autoload 'helm-imenu-in-all-buffers "helm-imenu" "\ +Preconfigured helm for fetching imenu entries in all buffers with similar mode as current. +A mode is similar as current if it is the same, it is derived i.e `derived-mode-p' +or it have an association in `helm-imenu-all-buffer-assoc'. + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-info" "helm-info.el" (23995 4638 454030 +;;;;;; 162000)) +;;; Generated autoloads from helm-info.el + +(autoload 'helm-info "helm-info" "\ +Preconfigured `helm' for searching Info files' indices. + +With a prefix argument \\[universal-argument], set REFRESH to non-nil. + +Optional parameter REFRESH, when non-nil, reevaluates +`helm-default-info-index-list'. If the variable has been +customized, set it to its saved value. If not, set it to its +standard value. See `custom-reevaluate-setting' for more. + +REFRESH is useful when new Info files are installed. If +`helm-default-info-index-list' has not been customized, the new +Info files are made available. + +\(fn &optional REFRESH)" t nil) + +(autoload 'helm-info-at-point "helm-info" "\ +Preconfigured `helm' for searching info at point. + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-locate" "helm-locate.el" (23995 4638 +;;;;;; 468480 454000)) +;;; Generated autoloads from helm-locate.el + +(autoload 'helm-projects-find-files "helm-locate" "\ +Find files with locate in `helm-locate-project-list'. +With a prefix arg refresh the database in each project. + +\(fn UPDATE)" t nil) + +(autoload 'helm-locate "helm-locate" "\ +Preconfigured `helm' for Locate. +Note: you can add locate options after entering pattern. +See 'man locate' for valid options and also `helm-locate-command'. + +You can specify a local database with prefix argument ARG. +With two prefix arg, refresh the current local db or create it +if it doesn't exists. + +To create a user specific db, use +\"updatedb -l 0 -o db_path -U directory\". +Where db_path is a filename matched by +`helm-locate-db-file-regexp'. + +\(fn ARG)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-man" "helm-man.el" (23995 4638 470648 +;;;;;; 856000)) +;;; Generated autoloads from helm-man.el + +(autoload 'helm-man-woman "helm-man" "\ +Preconfigured `helm' for Man and Woman pages. +With a prefix arg reinitialize the cache. + +\(fn ARG)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-misc" "helm-misc.el" (23995 4638 447993 +;;;;;; 29000)) +;;; Generated autoloads from helm-misc.el + +(autoload 'helm-world-time "helm-misc" "\ +Preconfigured `helm' to show world time. +Default action change TZ environment variable locally to emacs. + +\(fn)" t nil) + +(autoload 'helm-insert-latex-math "helm-misc" "\ +Preconfigured helm for latex math symbols completion. + +\(fn)" t nil) + +(autoload 'helm-ratpoison-commands "helm-misc" "\ +Preconfigured `helm' to execute ratpoison commands. + +\(fn)" t nil) + +(autoload 'helm-stumpwm-commands "helm-misc" "\ +Preconfigured helm for stumpwm commands. + +\(fn)" t nil) + +(autoload 'helm-minibuffer-history "helm-misc" "\ +Preconfigured `helm' for `minibuffer-history'. + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-mode" "helm-mode.el" (23995 4638 461864 +;;;;;; 977000)) +;;; Generated autoloads from helm-mode.el + +(autoload 'helm-comp-read "helm-mode" "\ +Read a string in the minibuffer, with helm completion. + +It is helm `completing-read' equivalent. + +- PROMPT is the prompt name to use. + +- COLLECTION can be a list, vector, obarray or hash-table. + It can be also a function that receives three arguments: + the values string, predicate and t. See `all-completions' for more details. + +Keys description: + +- TEST: A predicate called with one arg i.e candidate. + +- INITIAL-INPUT: Same as input arg in `helm'. + +- PRESELECT: See preselect arg of `helm'. + +- DEFAULT: This option is used only for compatibility with regular + Emacs `completing-read' (Same as DEFAULT arg of `completing-read'). + +- BUFFER: Name of helm-buffer. + +- MUST-MATCH: Candidate selected must be one of COLLECTION. + +- FUZZY: Enable fuzzy matching. + +- REVERSE-HISTORY: When non--nil display history source after current + source completion. + +- REQUIRES-PATTERN: Same as helm attribute, default is 0. + +- HISTORY: A list containing specific history, default is nil. + When it is non--nil, all elements of HISTORY are displayed in + a special source before COLLECTION. + +- INPUT-HISTORY: A symbol. the minibuffer input history will be + stored there, if nil or not provided, `minibuffer-history' + will be used instead. + +- CASE-FOLD: Same as `helm-case-fold-search'. + +- DEL-INPUT: Boolean, when non--nil (default) remove the partial + minibuffer input from HISTORY is present. + +- PERSISTENT-ACTION: A function called with one arg i.e candidate. + +- PERSISTENT-HELP: A string to document PERSISTENT-ACTION. + +- MODE-LINE: A string or list to display in mode line. + Default is `helm-comp-read-mode-line'. + +- KEYMAP: A keymap to use in this `helm-comp-read'. + (the keymap will be shared with history source) + +- NAME: The name related to this local source. + +- HEADER-NAME: A function to alter NAME, see `helm'. + +- EXEC-WHEN-ONLY-ONE: Bound `helm-execute-action-at-once-if-one' + to non--nil. (possibles values are t or nil). + +- VOLATILE: Use volatile attribute. + +- SORT: A predicate to give to `sort' e.g `string-lessp' + Use this only on small data as it is ineficient. + If you want to sort faster add a sort function to + FC-TRANSFORMER. + Note that FUZZY when enabled is already providing a sort function. + +- FC-TRANSFORMER: A `filtered-candidate-transformer' function + or a list of functions. + +- HIST-FC-TRANSFORMER: A `filtered-candidate-transformer' + function for the history source. + +- MARKED-CANDIDATES: If non--nil return candidate or marked candidates as a list. + +- NOMARK: When non--nil don't allow marking candidates. + +- ALISTP: (default is non--nil) See `helm-comp-read-get-candidates'. + +- CANDIDATES-IN-BUFFER: when non--nil use a source build with + `helm-source-in-buffer' which is much faster. + Argument VOLATILE have no effect when CANDIDATES-IN-BUFFER is non--nil. + +- MATCH-PART: Allow matching only one part of candidate. + See match-part documentation in `helm-source'. + +- MATCH-DYNAMIC: See match-dynamic in `helm-source-sync' + It have no effect when used with CANDIDATES-IN-BUFFER. + +- ALLOW-NEST: Allow nesting this `helm-comp-read' in a helm session. + See `helm'. + +- MULTILINE: See multiline in `helm-source'. + +- GROUP: See group in `helm-source'. + +Any prefix args passed during `helm-comp-read' invocation will be recorded +in `helm-current-prefix-arg', otherwise if prefix args were given before +`helm-comp-read' invocation, the value of `current-prefix-arg' will be used. +That's mean you can pass prefix args before or after calling a command +that use `helm-comp-read' See `helm-M-x' for example. + +\(fn PROMPT COLLECTION &key TEST INITIAL-INPUT DEFAULT PRESELECT (BUFFER \"*Helm Completions*\") MUST-MATCH FUZZY REVERSE-HISTORY (REQUIRES-PATTERN 0) HISTORY INPUT-HISTORY (CASE-FOLD helm-comp-read-case-fold-search) (DEL-INPUT t) (PERSISTENT-ACTION nil) (PERSISTENT-HELP \"DoNothing\") (MODE-LINE helm-comp-read-mode-line) HELP-MESSAGE (KEYMAP helm-comp-read-map) (NAME \"Helm Completions\") HEADER-NAME CANDIDATES-IN-BUFFER MATCH-PART MATCH-DYNAMIC EXEC-WHEN-ONLY-ONE QUIT-WHEN-NO-CAND (VOLATILE t) SORT FC-TRANSFORMER HIST-FC-TRANSFORMER MARKED-CANDIDATES NOMARK (ALISTP t) (CANDIDATE-NUMBER-LIMIT helm-candidate-number-limit) MULTILINE ALLOW-NEST (GROUP \\='helm))" nil nil) + +(autoload 'helm-read-file-name "helm-mode" "\ +Read a file name with helm completion. +It is helm `read-file-name' emulation. + +Argument PROMPT is the default prompt to use. + +Keys description: + +- NAME: Source name, default to \"Read File Name\". + +- INITIAL-INPUT: Where to start read file name, default to `default-directory'. + +- BUFFER: `helm-buffer' name default to \"*Helm Completions*\". + +- TEST: A predicate called with one arg 'candidate'. + +- NORET: Allow disabling helm-ff-RET (have no effect if helm-ff-RET + isn't bound to RET). + +- CASE-FOLD: Same as `helm-case-fold-search'. + +- PRESELECT: helm preselection. + +- HISTORY: Display HISTORY in a special source. + +- MUST-MATCH: Can be 'confirm, nil, or t. + +- FUZZY: Enable fuzzy matching when non-nil (Enabled by default). + +- MARKED-CANDIDATES: When non--nil return a list of marked candidates. + +- NOMARK: When non--nil don't allow marking candidates. + +- ALISTP: Don't use `all-completions' in history (take effect only on history). + +- PERSISTENT-ACTION-IF: a persistent if action function. + +- PERSISTENT-HELP: persistent help message. + +- MODE-LINE: A mode line message, default is `helm-read-file-name-mode-line-string'. + +\(fn PROMPT &key (NAME \"Read File Name\") (INITIAL-INPUT default-directory) (BUFFER \"*Helm file completions*\") TEST NORET (CASE-FOLD helm-file-name-case-fold-search) PRESELECT HISTORY MUST-MATCH (FUZZY t) DEFAULT MARKED-CANDIDATES (CANDIDATE-NUMBER-LIMIT helm-ff-candidate-number-limit) NOMARK (ALISTP t) (PERSISTENT-ACTION-IF \\='helm-find-files-persistent-action-if) (PERSISTENT-HELP \"Hit1 Expand Candidate, Hit2 or (C-u) Find file\") (MODE-LINE helm-read-file-name-mode-line-string))" nil nil) + +(defvar helm-mode nil "\ +Non-nil if Helm mode is enabled. +See the `helm-mode' command +for a description of this minor mode. +Setting this variable directly does not take effect; +either customize it (see the info node `Easy Customization') +or call the function `helm-mode'.") + +(custom-autoload 'helm-mode "helm-mode" nil) + +(autoload 'helm-mode "helm-mode" "\ +Toggle generic helm completion. + +All functions in Emacs that use `completing-read' +or `read-file-name' and friends will use helm interface +when this mode is turned on. + +However you can modify this behavior for functions of your choice +with `helm-completing-read-handlers-alist'. + +Also commands using `completion-in-region' will be helmized when +`helm-mode-handle-completion-in-region' is non nil, you can modify +this behavior with `helm-mode-no-completion-in-region-in-modes'. + +Called with a positive arg, turn on unconditionally, with a +negative arg turn off. +You can turn it on with `helm-mode'. + +Some crap emacs functions may not be supported, +e.g `ffap-alternate-file' and maybe others +You can add such functions to `helm-completing-read-handlers-alist' +with a nil value. + +About `ido-mode': +When you are using `helm-mode', DO NOT use `ido-mode', instead if you +want some commands use `ido', add these commands to +`helm-completing-read-handlers-alist' with `ido' as value. + +Note: This mode is incompatible with Emacs23. + +\(fn &optional ARG)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-net" "helm-net.el" (23995 4638 427991 +;;;;;; 953000)) +;;; Generated autoloads from helm-net.el + +(autoload 'helm-browse-url-firefox "helm-net" "\ +Same as `browse-url-firefox' but detach from emacs. + +So when you quit emacs you can keep your firefox session open +and not be prompted to kill firefox process. + +NOTE: Probably not supported on some systems (e.g Windows). + +\(fn URL &optional IGNORE)" t nil) + +(autoload 'helm-browse-url-opera "helm-net" "\ +Browse URL with opera browser and detach from emacs. + +So when you quit emacs you can keep your opera session open +and not be prompted to kill opera process. + +NOTE: Probably not supported on some systems (e.g Windows). + +\(fn URL &optional IGNORE)" t nil) + +(autoload 'helm-browse-url-chromium "helm-net" "\ +Browse URL with google chrome browser. + +\(fn URL &optional IGNORE)" t nil) + +(autoload 'helm-browse-url-uzbl "helm-net" "\ +Browse URL with uzbl browser. + +\(fn URL &optional IGNORE)" t nil) + +(autoload 'helm-browse-url-conkeror "helm-net" "\ +Browse URL with conkeror browser. + +\(fn URL &optional IGNORE)" t nil) + +(autoload 'helm-surfraw "helm-net" "\ +Preconfigured `helm' to search PATTERN with search ENGINE. + +\(fn PATTERN ENGINE)" t nil) + +(autoload 'helm-google-suggest "helm-net" "\ +Preconfigured `helm' for google search with google suggest. + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-occur" "helm-occur.el" (23995 4638 442119 +;;;;;; 851000)) +;;; Generated autoloads from helm-occur.el + +(autoload 'helm-occur "helm-occur" "\ +Preconfigured helm for searching lines matching pattern in `current-buffer'. + +When `helm-source-occur' is member of +`helm-sources-using-default-as-input' which is the default, +symbol at point is searched at startup. + +When a region is marked search only in this region by narrowing. + +To search in multiples buffers start from one of the commands listing +buffers (i.e. a helm command using `helm-source-buffers-list' like +`helm-mini') and use the multi occur buffers action. + +This is the helm implementation that collect lines matching pattern +like vanilla emacs `occur' but have nothing to do with it, the search +engine beeing completely different and also much faster. + +\(fn)" t nil) + +(autoload 'helm-occur-mode "helm-occur" "\ +Major mode to provide actions in helm moccur saved buffer. + +Special commands: +\\{helm-occur-mode-map} + +\(fn)" t nil) + +(autoload 'helm-occur-from-isearch "helm-occur" "\ +Invoke `helm-occur' from isearch. + +To use this bind it to a key in `isearch-mode-map'. + +\(fn)" t nil) + +(autoload 'helm-multi-occur-from-isearch "helm-occur" "\ +Invoke `helm-multi-occur' from isearch. + +With a prefix arg, reverse the behavior of +`helm-moccur-always-search-in-current'. +The prefix arg can be set before calling +`helm-multi-occur-from-isearch' or during the buffer selection. + +To use this bind it to a key in `isearch-mode-map'. + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-regexp" "helm-regexp.el" (23995 4638 +;;;;;; 457542 714000)) +;;; Generated autoloads from helm-regexp.el + +(autoload 'helm-regexp "helm-regexp" "\ +Preconfigured helm to build regexps. +`query-replace-regexp' can be run from there against found regexp. + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-ring" "helm-ring.el" (23995 4638 467358 +;;;;;; 867000)) +;;; Generated autoloads from helm-ring.el + +(autoload 'helm-mark-ring "helm-ring" "\ +Preconfigured `helm' for `helm-source-mark-ring'. + +\(fn)" t nil) + +(autoload 'helm-global-mark-ring "helm-ring" "\ +Preconfigured `helm' for `helm-source-global-mark-ring'. + +\(fn)" t nil) + +(autoload 'helm-all-mark-rings "helm-ring" "\ +Preconfigured `helm' for `helm-source-global-mark-ring' and `helm-source-mark-ring'. + +\(fn)" t nil) + +(autoload 'helm-register "helm-ring" "\ +Preconfigured `helm' for Emacs registers. + +\(fn)" t nil) + +(autoload 'helm-show-kill-ring "helm-ring" "\ +Preconfigured `helm' for `kill-ring'. +It is drop-in replacement of `yank-pop'. + +First call open the kill-ring browser, next calls move to next line. + +\(fn)" t nil) + +(autoload 'helm-execute-kmacro "helm-ring" "\ +Preconfigured helm for keyboard macros. +Define your macros with `f3' and `f4'. +See (info \"(emacs) Keyboard Macros\") for detailed infos. +This command is useful when used with persistent action. + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-semantic" "helm-semantic.el" (23995 4638 +;;;;;; 433498 614000)) +;;; Generated autoloads from helm-semantic.el + +(autoload 'helm-semantic "helm-semantic" "\ +Preconfigured `helm' for `semantic'. +If ARG is supplied, pre-select symbol at point instead of current + +\(fn ARG)" t nil) + +(autoload 'helm-semantic-or-imenu "helm-semantic" "\ +Preconfigured helm for `semantic' or `imenu'. +If ARG is supplied, pre-select symbol at point instead of current +semantic tag in scope. + +If `semantic-mode' is active in the current buffer, then use +semantic for generating tags, otherwise fall back to `imenu'. +Fill in the symbol at point by default. + +\(fn ARG)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-shell" "helm-shell.el" (23995 4638 429828 +;;;;;; 754000)) +;;; Generated autoloads from helm-shell.el + +(defalias 'helm-shell-prompts 'helm-comint-prompts) + +(defalias 'helm-shell-prompts-all 'helm-comint-prompts-all) + +;;;*** + +;;;### (autoloads nil "helm-sys" "helm-sys.el" (23995 4638 466220 +;;;;;; 502000)) +;;; Generated autoloads from helm-sys.el + +(defvar helm-top-poll-mode nil "\ +Non-nil if Helm-Top-Poll mode is enabled. +See the `helm-top-poll-mode' command +for a description of this minor mode. +Setting this variable directly does not take effect; +either customize it (see the info node `Easy Customization') +or call the function `helm-top-poll-mode'.") + +(custom-autoload 'helm-top-poll-mode "helm-sys" nil) + +(autoload 'helm-top-poll-mode "helm-sys" "\ +Refresh automatically helm top buffer once enabled. + +\(fn &optional ARG)" t nil) + +(autoload 'helm-top "helm-sys" "\ +Preconfigured `helm' for top command. + +\(fn)" t nil) + +(autoload 'helm-list-emacs-process "helm-sys" "\ +Preconfigured `helm' for emacs process. + +\(fn)" t nil) + +(autoload 'helm-xrandr-set "helm-sys" "\ +Preconfigured helm for xrandr. + +\(fn)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-tags" "helm-tags.el" (23995 4638 445164 +;;;;;; 259000)) +;;; Generated autoloads from helm-tags.el + +(autoload 'helm-etags-select "helm-tags" "\ +Preconfigured helm for etags. +If called with a prefix argument REINIT +or if any of the tag files have been modified, reinitialize cache. + +This function aggregates three sources of tag files: + + 1) An automatically located file in the parent directories, + by `helm-etags-get-tag-file'. + 2) `tags-file-name', which is commonly set by `find-tag' command. + 3) `tags-table-list' which is commonly set by `visit-tags-table' command. + +\(fn REINIT)" t nil) + +;;;*** + +;;;### (autoloads nil "helm-utils" "helm-utils.el" (23995 4638 432487 +;;;;;; 102000)) +;;; Generated autoloads from helm-utils.el + +(defvar helm-popup-tip-mode nil "\ +Non-nil if Helm-Popup-Tip mode is enabled. +See the `helm-popup-tip-mode' command +for a description of this minor mode. +Setting this variable directly does not take effect; +either customize it (see the info node `Easy Customization') +or call the function `helm-popup-tip-mode'.") + +(custom-autoload 'helm-popup-tip-mode "helm-utils" nil) + +(autoload 'helm-popup-tip-mode "helm-utils" "\ +Show help-echo informations in a popup tip at end of line. + +\(fn &optional ARG)" t nil) + +;;;*** + +;;;### (autoloads nil nil ("helm-easymenu.el" "helm-pkg.el" "helm-types.el" +;;;;;; "helm-x-files.el") (23995 4638 471463 881000)) + +;;;*** + +;; Local Variables: +;; version-control: never +;; no-byte-compile: t +;; no-update-autoloads: t +;; End: +;;; helm-autoloads.el ends here diff --git a/elpa/helm-20191031.839/helm-bookmark.el b/elpa/helm-20191031.839/helm-bookmark.el new file mode 100644 index 00000000..66f49cbb --- /dev/null +++ b/elpa/helm-20191031.839/helm-bookmark.el @@ -0,0 +1,737 @@ +;;; helm-bookmark.el --- Helm for Emacs regular Bookmarks. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: +(require 'cl-lib) +(require 'bookmark) +(require 'helm) +(require 'helm-lib) +(require 'helm-help) +(require 'helm-types) +(require 'helm-utils) +(require 'helm-info) +(require 'helm-adaptive) +(require 'helm-net) + +(declare-function helm-browse-project "helm-files" (arg)) +(declare-function addressbook-bookmark-edit "ext:addressbook-bookmark.el" (bookmark)) + +(defgroup helm-bookmark nil + "Predefined configurations for `helm.el'." + :group 'helm) + +(defcustom helm-bookmark-show-location nil + "Show location of bookmark on display." + :group 'helm-bookmark + :type 'boolean) + +(defcustom helm-bookmark-default-filtered-sources + (append '(helm-source-bookmark-org + helm-source-bookmark-files&dirs + helm-source-bookmark-helm-find-files + helm-source-bookmark-info + helm-source-bookmark-gnus + helm-source-bookmark-man + helm-source-bookmark-images + helm-source-bookmark-w3m) + (list 'helm-source-bookmark-uncategorized + 'helm-source-bookmark-set)) + "List of sources to use in `helm-filtered-bookmarks'." + :group 'helm-bookmark + :type '(repeat (choice symbol))) + + +(defface helm-bookmark-info + '((t (:foreground "green"))) + "Face used for W3m Emacs bookmarks (not w3m bookmarks)." + :group 'helm-bookmark) + +(defface helm-bookmark-w3m + '((t (:foreground "yellow"))) + "Face used for W3m Emacs bookmarks (not w3m bookmarks)." + :group 'helm-bookmark) + +(defface helm-bookmark-gnus + '((t (:foreground "magenta"))) + "Face used for Gnus bookmarks." + :group 'helm-bookmark) + +(defface helm-bookmark-man + '((t (:foreground "Orange4"))) + "Face used for Woman/man bookmarks." + :group 'helm-bookmark) + +(defface helm-bookmark-file + '((t (:foreground "Deepskyblue2"))) + "Face used for file bookmarks." + :group 'helm-bookmark) + +(defface helm-bookmark-file-not-found + '((t (:foreground "Slategray4"))) + "Face used for file bookmarks." + :group 'helm-bookmark) + +(defface helm-bookmark-directory + '((t (:inherit helm-ff-directory))) + "Face used for file bookmarks." + :group 'helm-bookmark) + +(defface helm-bookmark-addressbook + '((t (:foreground "tomato"))) + "Face used for addressbook bookmarks." + :group 'helm-bookmark) + + +(defvar helm-bookmark-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "C-c o") 'helm-bookmark-run-jump-other-window) + (define-key map (kbd "C-c C-o") 'helm-bookmark-run-jump-other-frame) + (define-key map (kbd "C-d") 'helm-bookmark-run-delete) + (define-key map (kbd "C-]") 'helm-bookmark-toggle-filename) + (define-key map (kbd "M-e") 'helm-bookmark-run-edit) + map) + "Generic Keymap for emacs bookmark sources.") + +(defclass helm-source-basic-bookmarks (helm-source-in-buffer helm-type-bookmark) + ((init :initform (lambda () + (bookmark-maybe-load-default-file) + (helm-init-candidates-in-buffer + 'global + (bookmark-all-names)))) + (filtered-candidate-transformer :initform 'helm-bookmark-transformer))) + +(defvar helm-source-bookmarks + (helm-make-source "Bookmarks" 'helm-source-basic-bookmarks) + "See (info \"(emacs)Bookmarks\").") + +(defun helm-bookmark-transformer (candidates _source) + (cl-loop for i in candidates + for loc = (bookmark-location i) + for len = (string-width i) + for trunc = (if (> len bookmark-bmenu-file-column) + (helm-substring i bookmark-bmenu-file-column) + i) + for sep = (make-string (- (+ bookmark-bmenu-file-column 2) + (length trunc)) + ? ) + if helm-bookmark-show-location + collect (cons (concat trunc sep (if (listp loc) (car loc) loc)) i) + else collect i)) + +(defun helm-bookmark-toggle-filename-1 (_candidate) + (let* ((real (helm-get-selection helm-buffer)) + (trunc (if (> (string-width real) bookmark-bmenu-file-column) + (helm-substring real bookmark-bmenu-file-column) + real)) + (loc (bookmark-location real))) + (setq helm-bookmark-show-location (not helm-bookmark-show-location)) + (helm-update (if helm-bookmark-show-location + (concat (regexp-quote trunc) + " +" + (regexp-quote + (if (listp loc) (car loc) loc))) + (regexp-quote real))))) + +(defun helm-bookmark-toggle-filename () + "Toggle bookmark location visibility." + (interactive) + (with-helm-alive-p + (helm-attrset 'toggle-filename + '(helm-bookmark-toggle-filename-1 . never-split)) + (helm-execute-persistent-action 'toggle-filename))) +(put 'helm-bookmark-toggle-filename 'helm-only t) + +(defun helm-bookmark-jump (candidate) + "Jump to bookmark action." + (let ((current-prefix-arg helm-current-prefix-arg) + non-essential) + (bookmark-jump candidate))) + +(defun helm-bookmark-jump-other-frame (candidate) + "Jump to bookmark in other frame action." + (let ((current-prefix-arg helm-current-prefix-arg) + non-essential) + (bookmark-jump candidate 'switch-to-buffer-other-frame))) + +(defun helm-bookmark-jump-other-window (candidate) + "Jump to bookmark in other window action." + (let (non-essential) + (bookmark-jump-other-window candidate))) + + +;;; bookmark-set +;; +(defvar helm-source-bookmark-set + (helm-build-dummy-source "Set Bookmark" + :filtered-candidate-transformer + (lambda (_candidates _source) + (list (or (and (not (string= helm-pattern "")) + helm-pattern) + "Enter a bookmark name to record"))) + :action '(("Set bookmark" . (lambda (candidate) + (if (string= helm-pattern "") + (message "No bookmark name given for record") + (bookmark-set candidate)))))) + "See (info \"(emacs)Bookmarks\").") + + +;;; Predicates +;; +(defconst helm-bookmark--non-file-filename " - no file -" + "Name to use for `filename' entry, for non-file bookmarks.") + +(defun helm-bookmark-gnus-bookmark-p (bookmark) + "Return non-nil if BOOKMARK is a Gnus bookmark. +BOOKMARK is a bookmark name or a bookmark record." + (or (eq (bookmark-get-handler bookmark) 'bmkext-jump-gnus) + (eq (bookmark-get-handler bookmark) 'gnus-summary-bookmark-jump) + (eq (bookmark-get-handler bookmark) 'bookmarkp-jump-gnus))) + +(defun helm-bookmark-w3m-bookmark-p (bookmark) + "Return non-nil if BOOKMARK is a W3m bookmark. +BOOKMARK is a bookmark name or a bookmark record." + (or (eq (bookmark-get-handler bookmark) 'bmkext-jump-w3m) + (eq (bookmark-get-handler bookmark) 'bookmark-w3m-bookmark-jump) + (eq (bookmark-get-handler bookmark) 'bookmarkp-jump-w3m))) + +(defun helm-bookmark-woman-bookmark-p (bookmark) + "Return non-nil if BOOKMARK is a Woman bookmark. +BOOKMARK is a bookmark name or a bookmark record." + (or (eq (bookmark-get-handler bookmark) 'bmkext-jump-woman) + (eq (bookmark-get-handler bookmark) 'woman-bookmark-jump) + (eq (bookmark-get-handler bookmark) 'bookmarkp-jump-woman))) + +(defun helm-bookmark-man-bookmark-p (bookmark) + "Return non-nil if BOOKMARK is a Man bookmark. +BOOKMARK is a bookmark name or a bookmark record." + (or (eq (bookmark-get-handler bookmark) 'bmkext-jump-man) + (eq (bookmark-get-handler bookmark) 'Man-bookmark-jump) + (eq (bookmark-get-handler bookmark) 'bookmarkp-jump-man))) + +(defun helm-bookmark-woman-man-bookmark-p (bookmark) + "Return non-nil if BOOKMARK is a Man or Woman bookmark. +BOOKMARK is a bookmark name or a bookmark record." + (or (helm-bookmark-man-bookmark-p bookmark) + (helm-bookmark-woman-bookmark-p bookmark))) + +(defun helm-bookmark-info-bookmark-p (bookmark) + "Return non-nil if BOOKMARK is an Info bookmark. +BOOKMARK is a bookmark name or a bookmark record." + (eq (bookmark-get-handler bookmark) 'Info-bookmark-jump)) + +(defun helm-bookmark-image-bookmark-p (bookmark) + "Return non-nil if BOOKMARK bookmarks an image file." + (if (stringp bookmark) + (assq 'image-type (assq bookmark bookmark-alist)) + (assq 'image-type bookmark))) + +(defun helm-bookmark-file-p (bookmark) + "Return non-nil if BOOKMARK bookmarks a file or directory. +BOOKMARK is a bookmark name or a bookmark record. +This excludes bookmarks of a more specific kind (Info, Gnus, and W3m)." + (let* ((filename (bookmark-get-filename bookmark)) + (isnonfile (equal filename helm-bookmark--non-file-filename))) + (and filename (not isnonfile) (not (bookmark-get-handler bookmark))))) + +(defun helm-bookmark-org-file-p (bookmark) + (let* ((filename (bookmark-get-filename bookmark))) + (or (string-suffix-p ".org" filename t) + (string-suffix-p ".org_archive" filename t)))) + +(defun helm-bookmark-helm-find-files-p (bookmark) + "Return non-nil if BOOKMARK bookmarks a `helm-find-files' session. +BOOKMARK is a bookmark name or a bookmark record." + (eq (bookmark-get-handler bookmark) 'helm-ff-bookmark-jump)) + +(defun helm-bookmark-addressbook-p (bookmark) + "Return non--nil if BOOKMARK is a contact recorded with addressbook-bookmark. +BOOKMARK is a bookmark name or a bookmark record." + (if (listp bookmark) + (string= (assoc-default 'type bookmark) "addressbook") + (string= (assoc-default + 'type (assoc bookmark bookmark-alist)) "addressbook"))) + +(defun helm-bookmark-uncategorized-bookmark-p (bookmark) + "Return non--nil if BOOKMARK match no known category." + (cl-loop for pred in '(helm-bookmark-org-file-p + helm-bookmark-addressbook-p + helm-bookmark-gnus-bookmark-p + helm-bookmark-w3m-bookmark-p + helm-bookmark-woman-man-bookmark-p + helm-bookmark-info-bookmark-p + helm-bookmark-image-bookmark-p + helm-bookmark-file-p + helm-bookmark-helm-find-files-p + helm-bookmark-addressbook-p) + never (funcall pred bookmark))) + +(defun helm-bookmark-filter-setup-alist (fn) + "Return a filtered `bookmark-alist' sorted alphabetically." + (cl-loop for b in bookmark-alist + for name = (car b) + when (funcall fn b) collect + (propertize name 'location (bookmark-location name)))) + +;;; Bookmark handlers +;; +(defvar w3m-async-exec) +(defun helm-bookmark-jump-w3m (bookmark) + "Jump to W3m bookmark BOOKMARK, setting a new tab. +If `browse-url-browser-function' is set to something else +than `w3m-browse-url' use it." + (require 'helm-net) + (let* ((file (or (bookmark-prop-get bookmark 'filename) + (bookmark-prop-get bookmark 'url))) + (buf (generate-new-buffer-name "*w3m*")) + (w3m-async-exec nil) + ;; If user don't have anymore w3m installed let it browse its + ;; bookmarks with default browser otherwise assume bookmark + ;; have been bookmarked from w3m and use w3m. + (browse-url-browser-function (or (and (fboundp 'w3m-browse-url) + (executable-find "w3m") + 'w3m-browse-url) + browse-url-browser-function)) + (really-use-w3m (equal browse-url-browser-function 'w3m-browse-url))) + (helm-browse-url file really-use-w3m) + (when really-use-w3m + (bookmark-default-handler + `("" (buffer . ,buf) . ,(bookmark-get-bookmark-record bookmark)))))) + +;; All bookmarks recorded with the handler provided with w3m +;; (`bookmark-w3m-bookmark-jump') will use our handler which open +;; the bookmark in a new tab or in an external browser depending +;; on `browse-url-browser-function'. +(defalias 'bookmark-w3m-bookmark-jump 'helm-bookmark-jump-w3m) + +;; Provide compatibility with old handlers provided in external +;; packages bookmark-extensions.el and bookmark+. +(defalias 'bmkext-jump-woman 'woman-bookmark-jump) +(defalias 'bmkext-jump-man 'Man-bookmark-jump) +(defalias 'bmkext-jump-w3m 'helm-bookmark-jump-w3m) +(defalias 'bmkext-jump-gnus 'gnus-summary-bookmark-jump) +(defalias 'bookmarkp-jump-gnus 'gnus-summary-bookmark-jump) +(defalias 'bookmarkp-jump-w3m 'helm-bookmark-jump-w3m) +(defalias 'bookmarkp-jump-woman 'woman-bookmark-jump) +(defalias 'bookmarkp-jump-man 'Man-bookmark-jump) + + +;;;; Filtered bookmark sources +;; +;; +(defclass helm-source-filtered-bookmarks (helm-source-in-buffer helm-type-bookmark) + ((filtered-candidate-transformer + :initform '(helm-adaptive-sort + helm-highlight-bookmark)))) + +;;; W3m bookmarks. +;; +(defun helm-bookmark-w3m-setup-alist () + "Specialized filter function for bookmarks w3m." + (helm-bookmark-filter-setup-alist 'helm-bookmark-w3m-bookmark-p)) + +(defvar helm-source-bookmark-w3m + (helm-make-source "Bookmark W3m" 'helm-source-filtered-bookmarks + :init (lambda () + (bookmark-maybe-load-default-file) + (helm-init-candidates-in-buffer + 'global (helm-bookmark-w3m-setup-alist))))) + +;;; Images +;; +(defun helm-bookmark-images-setup-alist () + "Specialized filter function for images bookmarks." + (helm-bookmark-filter-setup-alist 'helm-bookmark-image-bookmark-p)) + +(defvar helm-source-bookmark-images + (helm-make-source "Bookmark Images" 'helm-source-filtered-bookmarks + :init (lambda () + (bookmark-maybe-load-default-file) + (helm-init-candidates-in-buffer + 'global (helm-bookmark-images-setup-alist))))) + +;;; Woman Man +;; +(defun helm-bookmark-man-setup-alist () + "Specialized filter function for bookmarks w3m." + (helm-bookmark-filter-setup-alist 'helm-bookmark-woman-man-bookmark-p)) + +(defvar helm-source-bookmark-man + (helm-make-source "Bookmark Woman&Man" 'helm-source-filtered-bookmarks + :init (lambda () + (bookmark-maybe-load-default-file) + (helm-init-candidates-in-buffer + 'global (helm-bookmark-man-setup-alist))))) + +;;; Org files +;; +(defun helm-bookmark-org-setup-alist () + "Specialized filter function for Org file bookmarks." + (helm-bookmark-filter-setup-alist 'helm-bookmark-org-file-p)) + +(defvar helm-source-bookmark-org + (helm-make-source " Bookmarked Org files" 'helm-source-filtered-bookmarks + :init (lambda () + (bookmark-maybe-load-default-file) + (helm-init-candidates-in-buffer + 'global (helm-bookmark-org-setup-alist))))) + +;;; Gnus +;; +(defun helm-bookmark-gnus-setup-alist () + "Specialized filter function for bookmarks gnus." + (helm-bookmark-filter-setup-alist 'helm-bookmark-gnus-bookmark-p)) + +(defvar helm-source-bookmark-gnus + (helm-make-source "Bookmark Gnus" 'helm-source-filtered-bookmarks + :init (lambda () + (bookmark-maybe-load-default-file) + (helm-init-candidates-in-buffer + 'global (helm-bookmark-gnus-setup-alist))))) + +;;; Info +;; +(defun helm-bookmark-info-setup-alist () + "Specialized filter function for bookmarks info." + (helm-bookmark-filter-setup-alist 'helm-bookmark-info-bookmark-p)) + +(defvar helm-source-bookmark-info + (helm-make-source "Bookmark Info" 'helm-source-filtered-bookmarks + :init (lambda () + (bookmark-maybe-load-default-file) + (helm-init-candidates-in-buffer + 'global (helm-bookmark-info-setup-alist))))) + +;;; Files and directories +;; +(defun helm-bookmark-local-files-setup-alist () + "Specialized filter function for bookmarks locals files." + (helm-bookmark-filter-setup-alist 'helm-bookmark-file-p)) + +(defvar helm-source-bookmark-files&dirs + (helm-make-source "Bookmark Files&Directories" 'helm-source-filtered-bookmarks + :init (lambda () + (bookmark-maybe-load-default-file) + (helm-init-candidates-in-buffer + 'global (helm-bookmark-local-files-setup-alist))))) + +;;; Helm find files sessions. +;; +(defun helm-bookmark-helm-find-files-setup-alist () + "Specialized filter function for `helm-find-files' bookmarks." + (helm-bookmark-filter-setup-alist 'helm-bookmark-helm-find-files-p)) + +(defun helm-bookmark-browse-project (candidate) + "Run `helm-browse-project' from action." + (with-helm-default-directory + (bookmark-get-filename candidate) + (helm-browse-project nil))) + +(defun helm-bookmark-run-browse-project () + "Run `helm-bookmark-browse-project' from keyboard." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-bookmark-browse-project))) +(put 'helm-bookmark-run-browse-project 'helm-only t) + +(defvar helm-bookmark-find-files-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-bookmark-map) + (define-key map (kbd "C-x C-d") 'helm-bookmark-run-browse-project) + map)) + +(defclass helm-bookmark-override-inheritor (helm-source) ()) + +(defmethod helm--setup-source ((source helm-bookmark-override-inheritor)) + ;; Ensure `helm-source-in-buffer' method is called. + (call-next-method) + (setf (slot-value source 'action) + (helm-append-at-nth + (cl-loop for (name . action) in helm-type-bookmark-actions + unless (memq action '(helm-bookmark-jump-other-frame + helm-bookmark-jump-other-window)) + collect (cons name action)) + '(("Browse project" . helm-bookmark-browse-project)) 1)) + (setf (slot-value source 'keymap) helm-bookmark-find-files-map)) + +(defclass helm-bookmark-find-files-class (helm-source-filtered-bookmarks + helm-bookmark-override-inheritor) + ()) + +(defvar helm-source-bookmark-helm-find-files + (helm-make-source "Bookmark helm-find-files sessions" 'helm-bookmark-find-files-class + :init (lambda () + (bookmark-maybe-load-default-file) + (helm-init-candidates-in-buffer + 'global (helm-bookmark-helm-find-files-setup-alist))) + :persistent-action (lambda (_candidate) (ignore)) + :persistent-help "Do nothing")) + +;;; Uncategorized bookmarks +;; +(defun helm-bookmark-uncategorized-setup-alist () + "Specialized filter function for uncategorized bookmarks." + (helm-bookmark-filter-setup-alist 'helm-bookmark-uncategorized-bookmark-p)) + +(defvar helm-source-bookmark-uncategorized + (helm-make-source "Bookmark uncategorized" 'helm-source-filtered-bookmarks + :init (lambda () + (bookmark-maybe-load-default-file) + (helm-init-candidates-in-buffer + 'global (helm-bookmark-uncategorized-setup-alist))))) + +;;; Transformer +;; + +(defun helm-highlight-bookmark (bookmarks _source) + "Used as `filtered-candidate-transformer' to colorize bookmarks." + (let ((non-essential t)) + (cl-loop for i in bookmarks + for isfile = (bookmark-get-filename i) + for hff = (helm-bookmark-helm-find-files-p i) + for handlerp = (and (fboundp 'bookmark-get-handler) + (bookmark-get-handler i)) + for isw3m = (and (fboundp 'helm-bookmark-w3m-bookmark-p) + (helm-bookmark-w3m-bookmark-p i)) + for isgnus = (and (fboundp 'helm-bookmark-gnus-bookmark-p) + (helm-bookmark-gnus-bookmark-p i)) + for isman = (and (fboundp 'helm-bookmark-man-bookmark-p) ; Man + (helm-bookmark-man-bookmark-p i)) + for iswoman = (and (fboundp 'helm-bookmark-woman-bookmark-p) ; Woman + (helm-bookmark-woman-bookmark-p i)) + for isannotation = (bookmark-get-annotation i) + for isabook = (string= (bookmark-prop-get i 'type) + "addressbook") + for isinfo = (eq handlerp 'Info-bookmark-jump) + for loc = (bookmark-location i) + for len = (string-width i) + for trunc = (if (and helm-bookmark-show-location + (> len bookmark-bmenu-file-column)) + (helm-substring + i bookmark-bmenu-file-column) + i) + ;; Add a * if bookmark have annotation + if (and isannotation (not (string-equal isannotation ""))) + do (setq trunc (concat "*" (if helm-bookmark-show-location trunc i))) + for sep = (and helm-bookmark-show-location + (make-string (- (+ bookmark-bmenu-file-column 2) + (string-width trunc)) + ? )) + for bmk = (cond ( ;; info buffers + isinfo + (propertize trunc 'face 'helm-bookmark-info + 'help-echo isfile)) + ( ;; w3m buffers + isw3m + (propertize trunc 'face 'helm-bookmark-w3m + 'help-echo isfile)) + ( ;; gnus buffers + isgnus + (propertize trunc 'face 'helm-bookmark-gnus + 'help-echo isfile)) + ( ;; Man Woman + (or iswoman isman) + (propertize trunc 'face 'helm-bookmark-man + 'help-echo isfile)) + ( ;; Addressbook + isabook + (propertize trunc 'face 'helm-bookmark-addressbook)) + (;; Directories (helm-find-files) + hff + (if (and (file-remote-p isfile) + (not (file-remote-p isfile nil t))) + (propertize trunc 'face 'helm-bookmark-file-not-found + 'help-echo isfile) + (propertize trunc 'face 'helm-bookmark-directory + 'help-echo isfile))) + ( ;; Directories (dired) + (and isfile + ;; This is needed because `non-essential' + ;; is not working on Emacs-24.2 and the behavior + ;; of tramp seems to have changed since previous + ;; versions (Need to reenter password even if a + ;; first connection have been established, + ;; probably when host is named differently + ;; i.e machine/localhost) + (and (not (file-remote-p isfile)) + (file-directory-p isfile))) + (propertize trunc 'face 'helm-bookmark-directory + 'help-echo isfile)) + ( ;; Non existing files. + (and isfile + ;; Be safe and call `file-exists-p' + ;; only if file is not remote or + ;; remote but connected. + (or (and (file-remote-p isfile) + (not (file-remote-p isfile nil t))) + (not (file-exists-p isfile)))) + (propertize trunc 'face 'helm-bookmark-file-not-found + 'help-echo isfile)) + ( ;; regular files + t + (propertize trunc 'face 'helm-bookmark-file + 'help-echo isfile))) + collect (if helm-bookmark-show-location + (cons (concat bmk sep (if (listp loc) (car loc) loc)) + i) + (cons bmk i))))) + + +;;; Edit/rename/save bookmarks. +;; +;; +(defun helm-bookmark-edit-bookmark (bookmark-name) + "Edit bookmark's name and file name, and maybe save them. +BOOKMARK-NAME is the current (old) name of the bookmark to be renamed." + (let ((bmk (helm-bookmark-get-bookmark-from-name bookmark-name)) + (handler (bookmark-prop-get bookmark-name 'handler))) + (if (eq handler 'addressbook-bookmark-jump) + (addressbook-bookmark-edit + (assoc bmk bookmark-alist)) + (helm-bookmark-edit-bookmark-1 bookmark-name handler)))) + +(defun helm-bookmark-edit-bookmark-1 (bookmark-name handler) + (let* ((helm--reading-passwd-or-string t) + (bookmark-fname (bookmark-get-filename bookmark-name)) + (bookmark-loc (bookmark-prop-get bookmark-name 'location)) + (new-name (read-from-minibuffer "Name: " bookmark-name)) + (new-loc (read-from-minibuffer "FileName or Location: " + (or bookmark-fname + (if (consp bookmark-loc) + (car bookmark-loc) + bookmark-loc)))) + (docid (and (eq handler 'mu4e-bookmark-jump) + (read-number "Docid: " (cdr bookmark-loc))))) + (when docid + (setq new-loc (cons new-loc docid))) + (when (and (not (equal new-name "")) (not (equal new-loc "")) + (y-or-n-p "Save changes? ")) + (if bookmark-fname + (progn + (helm-bookmark-rename bookmark-name new-name 'batch) + (bookmark-set-filename new-name new-loc)) + (bookmark-prop-set + (bookmark-get-bookmark bookmark-name) 'location new-loc) + (helm-bookmark-rename bookmark-name new-name 'batch)) + (helm-bookmark-maybe-save-bookmark) + (list new-name new-loc)))) + +(defun helm-bookmark-maybe-save-bookmark () + "Increment save counter and maybe save `bookmark-alist'." + (setq bookmark-alist-modification-count (1+ bookmark-alist-modification-count)) + (when (bookmark-time-to-save-p) (bookmark-save))) + +(defun helm-bookmark-rename (old &optional new batch) + "Change bookmark's name from OLD to NEW. +Interactively: + If called from the keyboard, then prompt for OLD. + If called from the menubar, select OLD from a menu. +If NEW is nil, then prompt for its string value. + +If BATCH is non-nil, then do not rebuild the menu list. + +While the user enters the new name, repeated `C-w' inserts consecutive +words from the buffer into the new bookmark name." + (interactive (list (bookmark-completing-read "Old bookmark name"))) + (bookmark-maybe-historicize-string old) + (bookmark-maybe-load-default-file) + (save-excursion (skip-chars-forward " ") (setq bookmark-yank-point (point))) + (setq bookmark-current-buffer (current-buffer)) + (let ((newname (or new (read-from-minibuffer + "New name: " nil + (let ((now-map (copy-keymap minibuffer-local-map))) + (define-key now-map "\C-w" 'bookmark-yank-word) + now-map) + nil 'bookmark-history)))) + (bookmark-set-name old newname) + (setq bookmark-current-bookmark newname) + (unless batch (bookmark-bmenu-surreptitiously-rebuild-list)) + (helm-bookmark-maybe-save-bookmark) newname)) + +(defun helm-bookmark-run-edit () + "Run `helm-bookmark-edit-bookmark' from keyboard." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-bookmark-edit-bookmark))) +(put 'helm-bookmark-run-edit 'helm-only t) + + +(defun helm-bookmark-run-jump-other-frame () + "Jump to bookmark other frame from keyboard." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-bookmark-jump-other-frame))) +(put 'helm-bookmark-run-jump-other-frame 'helm-only t) + +(defun helm-bookmark-run-jump-other-window () + "Jump to bookmark from keyboard." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-bookmark-jump-other-window))) +(put 'helm-bookmark-run-jump-other-window 'helm-only t) + +(defun helm-bookmark-run-delete () + "Delete bookmark from keyboard." + (interactive) + (with-helm-alive-p + (when (y-or-n-p "Delete bookmark(s)?") + (helm-exit-and-execute-action 'helm-delete-marked-bookmarks)))) +(put 'helm-bookmark-run-delete 'helm-only t) + +(defun helm-bookmark-get-bookmark-from-name (bmk) + "Return bookmark name even if it is a bookmark with annotation. +e.g prepended with *." + (let ((bookmark (replace-regexp-in-string "\\`\\*" "" bmk))) + (if (assoc bookmark bookmark-alist) bookmark bmk))) + +(defun helm-delete-marked-bookmarks (_ignore) + "Delete this bookmark or all marked bookmarks." + (cl-dolist (i (helm-marked-candidates)) + (bookmark-delete (helm-bookmark-get-bookmark-from-name i) + 'batch))) + + +;;;###autoload +(defun helm-bookmarks () + "Preconfigured `helm' for bookmarks." + (interactive) + (helm :sources '(helm-source-bookmarks + helm-source-bookmark-set) + :buffer "*helm bookmarks*" + :default (buffer-name helm-current-buffer))) + +;;;###autoload +(defun helm-filtered-bookmarks () + "Preconfigured helm for bookmarks (filtered by category). +Optional source `helm-source-bookmark-addressbook' is loaded +only if external addressbook-bookmark package is installed." + (interactive) + (helm :sources helm-bookmark-default-filtered-sources + :prompt "Search Bookmark: " + :buffer "*helm filtered bookmarks*" + :default (list (thing-at-point 'symbol) + (buffer-name helm-current-buffer)))) + +(provide 'helm-bookmark) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-bookmark.el ends here diff --git a/elpa/helm-20191031.839/helm-buffers.el b/elpa/helm-20191031.839/helm-buffers.el new file mode 100644 index 00000000..1fa450e1 --- /dev/null +++ b/elpa/helm-20191031.839/helm-buffers.el @@ -0,0 +1,1152 @@ +;;; helm-buffers.el --- helm support for buffers. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'cl-lib) +(require 'helm) +(require 'helm-types) +(require 'helm-utils) +(require 'helm-grep) +(require 'helm-regexp) +(require 'helm-help) +(require 'helm-occur) + +(declare-function ido-make-buffer-list "ido" (default)) +(declare-function ido-add-virtual-buffers-to-list "ido") +(declare-function helm-comp-read "helm-mode") +(declare-function helm-browse-project "helm-files") + + +(defgroup helm-buffers nil + "Buffers related Applications and libraries for Helm." + :group 'helm) + +(defcustom helm-boring-buffer-regexp-list + '("\\` " "\\`\\*helm" "\\`\\*Echo Area" "\\`\\*Minibuf") + "The regexp list that match boring buffers. +Buffer candidates matching these regular expression will be +filtered from the list of candidates if the +`helm-skip-boring-buffers' candidate transformer is used." + :type '(repeat (choice regexp)) + :group 'helm-buffers) + +(defcustom helm-white-buffer-regexp-list nil + "The regexp list of not boring buffers. +These buffers will be displayed even if they match one of +`helm-boring-buffer-regexp-list'." + :type '(repeat (choice regexp)) + :group 'helm-buffers) + +(defcustom helm-buffers-favorite-modes '(lisp-interaction-mode + emacs-lisp-mode + text-mode + org-mode) + "List of preferred mode to open new buffers with." + :type '(repeat (choice function)) + :group 'helm-buffers) + +(defcustom helm-buffer-max-length 20 + "Max length of buffer names before truncate. +When disabled (nil) use the longest buffer-name length found." + :group 'helm-buffers + :type '(choice (const :tag "Disabled" nil) + (integer :tag "Length before truncate"))) + +(defcustom helm-buffer-details-flag t + "Always show details in buffer list when non--nil." + :group 'helm-buffers + :type 'boolean) + +(defcustom helm-buffers-fuzzy-matching nil + "Fuzzy matching buffer names when non--nil. +Only buffer names are fuzzy matched when this is enabled, +`major-mode' matching is not affected by this." + :group 'helm-buffers + :type 'boolean) + +(defcustom helm-buffer-skip-remote-checking nil + "Ignore checking for `file-exists-p' on remote files." + :group 'helm-buffers + :type 'boolean) + +(defcustom helm-buffers-truncate-lines t + "Truncate lines in `helm-buffers-list' when non--nil." + :group 'helm-buffers + :type 'boolean) + +(defcustom helm-buffers-left-margin-width helm-left-margin-width + "`left-margin-width' value for `helm-mini' and `helm-buffers-list'." + :group 'helm-buffers + :type 'integer) + +(defcustom helm-mini-default-sources '(helm-source-buffers-list + helm-source-recentf + helm-source-buffer-not-found) + "Default sources list used in `helm-mini'. + +When adding a source here it is up to you to ensure the library of +this source is accessible and properly loaded." + :group 'helm-buffers + :type '(repeat (choice symbol))) + +(defcustom helm-buffers-end-truncated-string "..." + "The string to display at end of truncated buffer names." + :type 'string + :group 'helm-buffers) + +(defcustom helm-buffers-column-separator " " + "Separator for columns in buffer listing." + :type 'string + :group 'helm-buffers) + +(defcustom helm-buffer--pretty-names '((dired-mode . "Dired") + (lisp-interaction-mode . "Lisp Inter")) + "An alist specifying pretty names for modes. +Most of the time buffer's `mode-name' is a string so no need to add it +here as there is no need to compute it, but sometimes it may be a +mode-line specification which may be costly to compute, in this case +add here the pretty name as a string to avoid this costly computation. +Also if some pretty names are too long you can add your own +abbreviation here." + :type '(alist :key-type symbol :value-type string) + :group 'helm-buffers) + +(defcustom helm-buffers-maybe-switch-to-tab nil + "Switch to buffer in its tab when non nil. +This have no effect when `tab-bar-mode' is not available." + :group 'helm-buffers + :type 'boolean) + + +;;; Faces +;; +;; +(defgroup helm-buffers-faces nil + "Customize the appearance of helm-buffers." + :prefix "helm-" + :group 'helm-buffers + :group 'helm-faces) + +(defface helm-buffer-saved-out + '((t (:foreground "red" :background "black"))) + "Face used for buffer files modified outside of emacs." + :group 'helm-buffers-faces) + +(defface helm-buffer-not-saved + '((t (:foreground "Indianred2"))) + "Face used for buffer files not already saved on disk." + :group 'helm-buffers-faces) + +(defface helm-buffer-modified + '((t :inherit font-lock-comment-face)) + "Face used for modified buffers." + :group 'helm-buffers-faces) + +(defface helm-buffer-size + '((((background dark)) :foreground "RosyBrown") + (((background light)) :foreground "SlateGray")) + "Face used for buffer size." + :group 'helm-buffers-faces) + +(defface helm-buffer-process + '((t (:foreground "Sienna3"))) + "Face used for process status in buffer." + :group 'helm-buffers-faces) + +(defface helm-buffer-directory + '((t (:foreground "DarkRed" :background "LightGray"))) + "Face used for directories in `helm-buffers-list'." + :group 'helm-buffers-faces) + +(defface helm-buffer-file + '((t :inherit font-lock-builtin-face)) + "Face for buffer file names in `helm-buffers-list'." + :group 'helm-buffers-faces) + +(defface helm-buffer-archive + '((t (:foreground "Gold"))) + "Face for archive file names in `helm-buffers-list'." + :group 'helm-buffers-faces) + +(defface helm-non-file-buffer + '((t (:inherit italic))) + "Face used for non-file buffers in `helm-buffers-list'." + :group 'helm-buffers-faces) + +(defvar helm-buffers-tick-counter nil + "Allows recording local changes to a non-file buffer. +Typical usage of this var is for modes that want to see if +their buffers have changed since last visit. +Such programs may want to record tick counter after visiting their +buffers like this: + + (setq helm-buffers-tick-counter (buffer-modified-tick)) + +Note that this variable is buffer-local.") +(make-variable-buffer-local 'helm-buffers-tick-counter) + + +;;; Buffers keymap +;; +(defvar helm-buffer-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + ;; No need to have separate command for grep and zgrep + ;; as we don't use recursivity for buffers. + ;; So use zgrep for both as it is capable to handle non--compressed files. + (define-key map (kbd "M-g s") 'helm-buffer-run-zgrep) + (define-key map (kbd "C-s") 'helm-buffers-run-occur) + (define-key map (kbd "C-x C-d") 'helm-buffers-run-browse-project) + (define-key map (kbd "C-c o") 'helm-buffer-switch-other-window) + (define-key map (kbd "C-c C-o") 'helm-buffer-switch-other-frame) + (define-key map (kbd "C-c =") 'helm-buffer-run-ediff) + (define-key map (kbd "M-=") 'helm-buffer-run-ediff-merge) + (define-key map (kbd "C-=") 'helm-buffer-diff-persistent) + (define-key map (kbd "M-G") 'helm-buffer-revert-persistent) + (define-key map (kbd "C-c d") 'helm-buffer-run-kill-persistent) + (define-key map (kbd "M-D") 'helm-buffer-run-kill-buffers) + (define-key map (kbd "C-x C-s") 'helm-buffer-save-persistent) + (define-key map (kbd "C-x s") 'helm-buffer-run-save-some-buffers) + (define-key map (kbd "C-M-%") 'helm-buffer-run-query-replace-regexp) + (define-key map (kbd "M-%") 'helm-buffer-run-query-replace) + (define-key map (kbd "M-R") 'helm-buffer-run-rename-buffer) + (define-key map (kbd "M-m") 'helm-toggle-all-marks) + (define-key map (kbd "M-a") 'helm-mark-all) + (define-key map (kbd "C-]") 'helm-toggle-buffers-details) + (define-key map (kbd "C-c a") 'helm-buffers-toggle-show-hidden-buffers) + (define-key map (kbd "C-M-SPC") 'helm-buffers-mark-similar-buffers) + (when (fboundp 'tab-bar-mode) + (define-key map (kbd "C-c C-t") 'helm-buffers-switch-to-buffer-new-tab)) + map) + "Keymap for buffer sources in helm.") + +(defvar helm-buffers-ido-virtual-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "C-c o") 'helm-ff-run-switch-other-window) + (define-key map (kbd "C-c C-o") 'helm-ff-run-switch-other-frame) + (define-key map (kbd "M-g s") 'helm-ff-run-grep) + (define-key map (kbd "M-g z") 'helm-ff-run-zgrep) + (define-key map (kbd "M-D") 'helm-ff-run-delete-file) + (define-key map (kbd "C-c C-x") 'helm-ff-run-open-file-externally) + map)) + + +(defvar helm-buffer-max-len-mode nil) +(defvar helm-buffers-in-project-p nil) +(defvar helm-source-buffers-list nil) + +(defun helm-buffers-list--init () + (require 'dired) + ;; Issue #51 Create the list before `helm-buffer' creation. + ;; We were using a global cache in the past and 'candidates was + ;; bound to this cache, this was a problem when using more than one + ;; source with a different 'buffer-list fn as the same cache was + ;; reused in each source (issue #1907), now 'candidates attr is set + ;; directly so that each list of candidates is local to source. + (helm-attrset 'candidates (funcall (helm-attr 'buffer-list))) + (let ((result (cl-loop with allbufs = (memq 'helm-shadow-boring-buffers + (helm-attr + 'filtered-candidate-transformer + helm-source-buffers-list)) + for b in (if allbufs + (helm-attr 'candidates) + (helm-skip-boring-buffers + (helm-attr 'candidates) + helm-source-buffers-list)) + maximize (length b) into len-buf + maximize (length (helm-buffer--format-mode-name b)) + into len-mode + finally return (cons len-buf len-mode)))) + (unless (default-value 'helm-buffer-max-length) + (helm-set-local-variable 'helm-buffer-max-length (car result))) + (unless (default-value 'helm-buffer-max-len-mode) + (helm-set-local-variable 'helm-buffer-max-len-mode (cdr result))))) + +(defclass helm-source-buffers (helm-source-sync helm-type-buffer) + ((buffer-list + :initarg :buffer-list + :initform #'helm-buffer-list + :custom function + :documentation + " A function with no arguments to create buffer list.") + (init :initform 'helm-buffers-list--init) + (multimatch :initform nil) + (match :initform 'helm-buffers-match-function) + (persistent-action :initform 'helm-buffers-list-persistent-action) + (keymap :initform helm-buffer-map) + (migemo :initform 'nomultimatch) + (volatile :initform t) + (nohighlight :initform t) + (resume :initform (lambda () (setq helm-buffers-in-project-p nil))) + (help-message :initform 'helm-buffer-help-message))) + +(cl-defun helm-buffers-create-new-buffer-1 (candidate &optional (display-func 'switch-to-buffer)) + (let ((mjm (or (and helm-current-prefix-arg + (intern-soft (helm-comp-read + "Major-mode: " + helm-buffers-favorite-modes))) + (cl-loop for (r . m) in auto-mode-alist + when (string-match r candidate) + return m))) + (buffer (get-buffer-create candidate))) + (if mjm + (with-current-buffer buffer (funcall mjm)) + (set-buffer-major-mode buffer)) + (funcall display-func buffer))) + +(defun helm-buffers-create-new-buffer (candidate) + (helm-buffers-create-new-buffer-1 candidate)) + +(defun helm-buffers-create-new-buffer-ow (candidate) + (helm-buffers-create-new-buffer-1 candidate 'switch-to-buffer-other-window)) + +(defun helm-buffers-not-found-run-switch-ow () + "Run create new buffer other window action from keymap." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-buffers-create-new-buffer-ow))) +(put 'helm-buffers-not-found-run-switch-ow 'helm-only t) + +(defun helm-buffers-create-new-buffer-of (candidate) + (helm-buffers-create-new-buffer-1 candidate 'switch-to-buffer-other-frame)) + +(defun helm-buffers-not-found-run-switch-of () + "Run create new buffer other frame action from keymap." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-buffers-create-new-buffer-of))) +(put 'helm-buffers-not-found-run-switch-of 'helm-only t) + +(defvar helm-buffer-not-found-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "C-c o") 'helm-buffers-not-found-run-switch-ow) + (define-key map (kbd "C-c C-o") 'helm-buffers-not-found-run-switch-of) + map) + "Keymap for `helm-source-buffer-not-found' source.") + +(defvar helm-source-buffer-not-found + (helm-build-dummy-source + "Create buffer" + :action (helm-make-actions + "Create buffer (C-u choose mode)" + #'helm-buffers-create-new-buffer + "Create buffer other window (C-u choose mode)" + #'helm-buffers-create-new-buffer-ow + "Create buffer other frame (C-u choose mode)" + #'helm-buffers-create-new-buffer-of) + :keymap helm-buffer-not-found-map)) + +(defvar ido-temp-list) +(defvar ido-ignored-list) +(defvar ido-process-ignore-lists) +(defvar ido-use-virtual-buffers) +(defvar ido-virtual-buffers) + +(defvar helm-source-ido-virtual-buffers + (helm-build-sync-source "Ido virtual buffers" + :candidates (lambda () + (let (ido-temp-list + ido-ignored-list + (ido-process-ignore-lists t)) + (when ido-use-virtual-buffers + (ido-add-virtual-buffers-to-list) + ido-virtual-buffers))) + :fuzzy-match helm-buffers-fuzzy-matching + :keymap helm-buffers-ido-virtual-map + :help-message 'helm-buffers-ido-virtual-help-message + :action '(("Find file" . helm-find-many-files) + ("Find file other window" . find-file-other-window) + ("Find file other frame" . find-file-other-frame) + ("Find file as root" . helm-find-file-as-root) + ("Grep File(s) `C-u recurse'" . helm-find-files-grep) + ("Zgrep File(s) `C-u Recurse'" . helm-ff-zgrep) + ("View file" . view-file) + ("Delete file(s)" . helm-delete-marked-files) + ("Open file externally (C-u to choose)" + . helm-open-file-externally)))) + + +(defvar ido-use-virtual-buffers) +(defvar ido-ignore-buffers) +(defun helm-buffer-list () + "Return the current list of buffers. +Currently visible buffers are put at the end of the list. +See `ido-make-buffer-list' for more infos." + (require 'ido) + (let ((ido-process-ignore-lists t) + ido-ignored-list + ido-ignore-buffers + ido-use-virtual-buffers) + (ido-make-buffer-list nil))) + +(defun helm-buffer-size (buffer) + "Return size of BUFFER." + (with-current-buffer buffer + (save-restriction + (widen) + (helm-file-human-size + (- (position-bytes (point-max)) + (position-bytes (point-min))))))) + +(defun helm-buffer--show-details (buf-name prefix help-echo + size mode dir face1 face2 + proc details type) + (append + (list + (concat prefix + (propertize buf-name 'face face1 + 'help-echo help-echo + 'type type))) + (and details + (list size mode + (propertize + (if proc + (format "(%s %s in `%s')" + (process-name proc) + (process-status proc) dir) + (format "(in `%s')" dir)) + 'face face2))))) + +(defun helm-buffer--format-mode-name (buf) + "Prevent using `format-mode-line' as much as possible." + (with-current-buffer buf + (helm-acond ((assq major-mode helm-buffer--pretty-names) + (cdr it)) + ((stringp mode-name) mode-name) + (t (format-mode-line mode-name))))) + +(defun helm-buffer--details (buffer &optional details) + (require 'dired) + (let* ((mode (helm-buffer--format-mode-name buffer)) + (buf (get-buffer buffer)) + (size (propertize (helm-buffer-size buf) + 'face 'helm-buffer-size)) + (proc (get-buffer-process buf)) + (dir (with-current-buffer buffer + (helm-aif default-directory (abbreviate-file-name it)))) + (file-name (helm-aif (buffer-file-name buf) (abbreviate-file-name it))) + (name (buffer-name buf)) + (name-prefix (when (and dir (file-remote-p dir)) + (propertize "@ " 'face 'helm-ff-prefix))) + (archive-p (and (fboundp 'tramp-archive-file-name-p) + (tramp-archive-file-name-p dir)))) + (when name-prefix + ;; Remote tramp buffer names may be hexified, make them more readable. + (setq dir (helm-url-unhex-string dir) + name (helm-url-unhex-string name))) + ;; Handle tramp archive buffers specially. + (if archive-p + (helm-buffer--show-details + name name-prefix file-name size mode dir + 'helm-buffer-archive 'helm-buffer-process nil details 'filebuf) + ;; No fancy things on remote buffers. + (if (and name-prefix helm-buffer-skip-remote-checking) + (helm-buffer--show-details + name name-prefix file-name size mode dir + 'helm-buffer-file 'helm-buffer-process nil details 'filebuf) + (cond + (;; A dired buffer. + (rassoc buf dired-buffers) + (helm-buffer--show-details + name name-prefix dir size mode dir + 'helm-buffer-directory 'helm-buffer-process nil details 'dired)) + ;; A buffer file modified somewhere outside of emacs.=>red + ((and file-name + (file-exists-p file-name) + (not (verify-visited-file-modtime buf))) + (helm-buffer--show-details + name name-prefix file-name size mode dir + 'helm-buffer-saved-out 'helm-buffer-process nil details 'modout)) + ;; A new buffer file not already saved on disk (or a deleted file) .=>indianred2 + ((and file-name (not (file-exists-p file-name))) + (helm-buffer--show-details + name name-prefix file-name size mode dir + 'helm-buffer-not-saved 'helm-buffer-process nil details 'notsaved)) + ;; A buffer file modified and not saved on disk.=>orange + ((and file-name (buffer-modified-p buf)) + (helm-buffer--show-details + name name-prefix file-name size mode dir + 'helm-buffer-modified 'helm-buffer-process nil details 'mod)) + ;; A buffer file not modified and saved on disk.=>green + (file-name + (helm-buffer--show-details + name name-prefix file-name size mode dir + 'helm-buffer-file 'helm-buffer-process nil details 'filebuf)) + ;; A non-file, modified buffer + ((with-current-buffer name + (and helm-buffers-tick-counter + (/= helm-buffers-tick-counter (buffer-modified-tick)))) + (helm-buffer--show-details + name (and proc name-prefix) dir size mode dir + 'helm-buffer-modified 'helm-buffer-process proc details 'nofile-mod)) + ;; Any non--file buffer.=>italic + (t + (helm-buffer--show-details + name (and proc name-prefix) dir size mode dir + 'helm-non-file-buffer 'helm-buffer-process proc details 'nofile))))))) + +(defun helm-highlight-buffers (buffers _source) + "Transformer function to highlight BUFFERS list. +Should be called after others transformers i.e (boring buffers)." + (cl-loop for i in buffers + for (name size mode meta) = (if helm-buffer-details-flag + (helm-buffer--details i 'details) + (helm-buffer--details i)) + for truncbuf = (if (> (string-width name) helm-buffer-max-length) + (helm-substring-by-width + name helm-buffer-max-length + helm-buffers-end-truncated-string) + (concat name + (make-string + (- (+ helm-buffer-max-length + (length + helm-buffers-end-truncated-string)) + (string-width name)) + ? ))) + for len = (length mode) + when (> len helm-buffer-max-len-mode) + do (setq helm-buffer-max-len-mode len) + for fmode = (concat (make-string + (- (max helm-buffer-max-len-mode len) len) ? ) + mode) + ;; The max length of a number should be 1023.9X where X is the + ;; units, this is 7 characters. + for formatted-size = (and size (format "%7s" size)) + collect (let ((helm-pattern (helm-buffers--pattern-sans-filters + (and helm-buffers-fuzzy-matching "")))) + (cons (if helm-buffer-details-flag + (concat + (funcall helm-fuzzy-matching-highlight-fn + truncbuf) + helm-buffers-column-separator + formatted-size + helm-buffers-column-separator + fmode + helm-buffers-column-separator + meta) + (funcall helm-fuzzy-matching-highlight-fn name)) + (get-buffer i))))) + +(defun helm-buffer--get-preselection (buffer) + (let ((bufname (buffer-name buffer))) + (when (and bufname + (file-remote-p (with-current-buffer bufname + default-directory))) + (setq bufname (concat "@ " (helm-url-unhex-string bufname)))) + (concat "^" + (if (and (null helm-buffer-details-flag) + (numberp helm-buffer-max-length) + (> (string-width bufname) + helm-buffer-max-length)) + (regexp-quote + (helm-substring-by-width + bufname helm-buffer-max-length + helm-buffers-end-truncated-string)) + (concat (regexp-quote bufname) + (if helm-buffer-details-flag + "$" "[[:blank:]]+")))))) + +(defun helm-toggle-buffers-details () + (interactive) + (with-helm-alive-p + (let* ((buf (helm-get-selection)) + (preselect (helm-buffer--get-preselection buf))) + (setq helm-buffer-details-flag (not helm-buffer-details-flag)) + (helm-update (lambda () + (helm-awhile (re-search-forward preselect nil t) + (helm-mark-current-line) + (when (equal buf (helm-get-selection)) + (cl-return t)))))))) +(put 'helm-toggle-buffers-details 'helm-only t) + +(defun helm-buffers--pattern-sans-filters (&optional separator) + (cl-loop for p in (helm-mm-split-pattern helm-pattern) + unless (member (substring p 0 1) '("*" "/" "@" "!")) + collect p into lst + finally return (mapconcat 'identity lst (or separator " ")))) + +(defun helm-buffers-sort-transformer (candidates source) + (if (string= helm-pattern "") + candidates + (if helm-buffers-fuzzy-matching + (let ((helm-pattern (helm-buffers--pattern-sans-filters))) + (funcall helm-fuzzy-sort-fn candidates source)) + (sort candidates + (lambda (s1 s2) + (< (string-width s1) (string-width s2))))))) + +(defun helm-buffers-mark-similar-buffers-1 (&optional type) + (with-helm-window + (let* ((src (helm-get-current-source)) + (type (or type + (get-text-property + 0 'type (helm-get-selection nil 'withprop src))))) + (save-excursion + (goto-char (helm-get-previous-header-pos)) + (helm-next-line) + (let* ((next-head (helm-get-next-header-pos)) + (end (and next-head + (save-excursion + (goto-char next-head) + (forward-line -1) + (point)))) + (maxpoint (or end (point-max)))) + (while (< (point) maxpoint) + (helm-mark-current-line) + (let ((cand (helm-get-selection nil 'withprop src))) + (when (and (not (helm-this-visible-mark)) + (eq (get-text-property 0 'type cand) type)) + (helm-make-visible-mark))) + (forward-line 1) (end-of-line)))) + (helm-mark-current-line) + (helm-display-mode-line src t) + (when helm-marked-candidates + (message "%s candidates marked" (length helm-marked-candidates)))))) + +(defun helm-buffers-mark-similar-buffers () + "Mark All buffers that have same property `type' than current. +i.e same color." + (interactive) + (with-helm-alive-p + (let ((marked (helm-marked-candidates))) + (if (and (>= (length marked) 1) + (with-helm-window helm-visible-mark-overlays)) + (helm-unmark-all) + (helm-buffers-mark-similar-buffers-1))))) +(put 'helm-buffers-mark-similar-buffers 'helm-only t) + + +;;; match functions +;; +(defun helm-buffer--match-mjm (pattern mjm) + (when (string-match "\\`\\*" pattern) + (cl-loop with patterns = (split-string (substring pattern 1) ",") + for pat in patterns + if (string-match "\\`!" pat) + collect (string-match (substring pat 1) mjm) into neg + else collect (string-match pat mjm) into pos + finally return + (let ((neg-test (cl-loop for i in neg thereis (numberp i))) + (pos-test (cl-loop for i in pos thereis (numberp i)))) + (or + (and neg (not pos) (not neg-test)) + (and pos pos-test) + (and neg neg-test (not neg-test))))))) + +(defvar helm-buffer--memo-hash (make-hash-table :test 'equal)) +(defun helm-buffer--memo-pattern (pattern) + (or (gethash pattern helm-buffer--memo-hash) + (puthash pattern (helm--mapconcat-pattern pattern) + helm-buffer--memo-hash))) + +(defun helm-buffer--match-pattern (pattern candidate &optional nofuzzy) + (let ((bfn (if (and helm-buffers-fuzzy-matching + (not nofuzzy) + (not helm-migemo-mode) + (not (string-match "\\`\\^" pattern))) + #'helm-buffer--memo-pattern + #'identity)) + (mfn (if helm-migemo-mode + #'helm-mm-migemo-string-match #'string-match))) + (if (string-match "\\`!" pattern) + (not (funcall mfn (funcall bfn (substring pattern 1)) + candidate)) + (funcall mfn (funcall bfn pattern) candidate)))) + +(defun helm-buffers--match-from-mjm (candidate) + (let* ((cand (replace-regexp-in-string "^\\s-\\{1\\}" "" candidate)) + (buf (get-buffer cand)) + (regexp (cl-loop with pattern = helm-pattern + for p in (helm-mm-split-pattern pattern) + when (string-match "\\`\\*" p) + return p))) + (if regexp + (when buf + (with-current-buffer buf + (let ((mjm (symbol-name major-mode))) + (helm-buffer--match-mjm regexp mjm)))) + t))) + +(defun helm-buffers--match-from-pat (candidate) + (let* ((regexp-list (cl-loop with pattern = helm-pattern + for p in (helm-mm-split-pattern pattern) + unless (string-match + "\\`\\(\\*\\|/\\|@\\)" p) + collect p)) + (nofuzzy (cdr regexp-list))) + (if regexp-list + (cl-loop for re in regexp-list + always (helm-buffer--match-pattern re candidate nofuzzy)) + t))) + +(defun helm-buffers--match-from-inside (candidate) + (let* ((cand (replace-regexp-in-string "^\\s-\\{1\\}" "" candidate)) + (buf (get-buffer cand)) + (regexp (cl-loop with pattern = helm-pattern + for p in (helm-mm-split-pattern pattern) + when (string-match "\\`@\\(.*\\)" p) + return (match-string 1 p)))) + (if (and buf regexp) + (with-current-buffer buf + (save-excursion + (goto-char (point-min)) + (if helm-migemo-mode + (helm-mm-migemo-forward regexp nil t) + (re-search-forward regexp nil t)))) + t))) + +(defun helm-buffers--match-from-directory (candidate) + (let* ((cand (replace-regexp-in-string "^\\s-\\{1\\}" "" candidate)) + (buf (get-buffer cand)) + (buf-fname (or (buffer-file-name buf) + (car-safe (rassoc buf dired-buffers)))) + (regexps (cl-loop with pattern = helm-pattern + for p in (helm-mm-split-pattern pattern) + when (string-match "\\`/" p) + collect p))) + (if regexps + (cl-loop for re in regexps + thereis + (and buf-fname + (string-match + (substring re 1) (helm-basedir buf-fname)))) + t))) + +(defun helm-buffers-match-function (candidate) + "Default function to match buffers." + (and (helm-buffers--match-from-pat candidate) + (helm-buffers--match-from-mjm candidate) + (helm-buffers--match-from-inside candidate) + (helm-buffers--match-from-directory candidate))) + + +(defun helm-buffer-query-replace-1 (&optional regexp-flag buffers) + "Query replace in marked buffers. +If REGEXP-FLAG is given use `query-replace-regexp'." + (let ((prompt (if regexp-flag "Query replace regexp" "Query replace")) + (bufs (or buffers (helm-marked-candidates))) + (helm--reading-passwd-or-string t)) + (cl-loop with args = (query-replace-read-args prompt regexp-flag t) + for buf in bufs + do + (save-window-excursion + (switch-to-buffer buf) + (save-excursion + (let ((case-fold-search t)) + (goto-char (point-min)) + (apply #'perform-replace + (list (nth 0 args) (nth 1 args) + t regexp-flag (nth 2 args) nil + multi-query-replace-map)))))))) + +(defun helm-buffer-query-replace-regexp (_candidate) + (helm-buffer-query-replace-1 'regexp)) + +(defun helm-buffer-query-replace (_candidate) + (helm-buffer-query-replace-1)) + +(defun helm-buffer-toggle-diff (candidate) + "Toggle diff buffer CANDIDATE with it's file." + (helm-aif (get-buffer-window "*Diff*" 'visible) + (progn (kill-buffer "*Diff*") + (set-window-buffer it helm-current-buffer)) + (let ((buf (get-buffer candidate))) + (if (buffer-file-name buf) + (diff-buffer-with-file buf) + (user-error "Buffer `%s' is not associated to a file" + (buffer-name buf)))))) + +(defun helm-buffer-diff-persistent () + "Toggle diff buffer without quitting helm." + (interactive) + (with-helm-alive-p + (helm-attrset 'diff-action 'helm-buffer-toggle-diff) + (helm-execute-persistent-action 'diff-action))) +(put 'helm-buffer-diff-persistent 'helm-only t) + +(defun helm-revert-buffer (candidate) + (with-current-buffer candidate + (helm-aif (buffer-file-name) + (and (file-exists-p it) (revert-buffer t t))))) + +(defun helm-revert-marked-buffers (_ignore) + (mapc 'helm-revert-buffer (helm-marked-candidates))) + +(defun helm-buffer-revert-and-update (_candidate) + (with-helm-buffer + (let ((marked (helm-marked-candidates)) + (preselect (helm-buffers--quote-truncated-buffer + (helm-get-selection)))) + (cl-loop for buf in marked do (helm-revert-buffer buf)) + (when helm-marked-candidates (helm-unmark-all)) + (helm-update preselect)))) + +(defun helm-buffer-revert-persistent () + "Revert buffer without quitting helm." + (interactive) + (with-helm-alive-p + (helm-attrset 'revert-action '(helm-buffer-revert-and-update . never-split)) + (helm-execute-persistent-action 'revert-action))) +(put 'helm-buffer-revert-persistent 'helm-only t) + +(defun helm-buffer-save-and-update (_candidate) + (with-helm-buffer + (let ((marked (helm-marked-candidates)) + (preselect (helm-get-selection nil t)) + (enable-recursive-minibuffers t)) + (cl-assert marked nil "No buffers need to be saved") + (cl-loop for buf in marked do + (with-current-buffer (get-buffer buf) + (when (buffer-file-name) (save-buffer)))) + (when helm-marked-candidates (helm-unmark-all)) + (helm-update (regexp-quote preselect))))) + +(defun helm-buffer-save-some-buffers (_candidate) + (helm-buffers-mark-similar-buffers-1 'mod) + (helm-buffer-save-and-update nil)) + +(defun helm-buffer-run-save-some-buffers () + "Save unsaved file buffers without quitting helm." + (interactive) + (with-helm-alive-p + (helm-attrset 'save-some-action '(helm-buffer-save-some-buffers . never-split)) + (helm-execute-persistent-action 'save-some-action))) +(put 'helm-buffer-run-save-some-buffers 'helm-only t) + +(defun helm-buffer-save-persistent () + "Save buffer without quitting helm." + (interactive) + (with-helm-alive-p + (helm-attrset 'save-action '(helm-buffer-save-and-update . never-split)) + (helm-execute-persistent-action 'save-action))) +(put 'helm-buffer-save-persistent 'helm-only t) + +(defun helm-buffers-rename-buffer (candidate) + (with-current-buffer candidate + (rename-buffer (helm-read-string "New name: " (buffer-name)) t))) + +(defun helm-buffer-run-rename-buffer () + "Run rename buffer action from `helm-source-buffers-list'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-buffers-rename-buffer))) +(put 'helm-buffer-run-rename-buffer 'helm-only t) + +(defun helm-buffer-run-kill-persistent () + "Kill buffer without quitting helm." + (interactive) + (with-helm-alive-p + (helm-attrset 'kill-action '(helm-buffers-persistent-kill . never-split)) + (helm-execute-persistent-action 'kill-action))) +(put 'helm-buffer-run-kill-persistent 'helm-only t) + +(defun helm-kill-marked-buffers (_ignore) + (let* ((bufs (helm-marked-candidates)) + (killed-bufs (cl-count-if 'kill-buffer bufs))) + (when (buffer-live-p helm-buffer) + (with-helm-buffer + (setq helm-marked-candidates nil + helm-visible-mark-overlays nil))) + (message "Killed %s buffer(s)" killed-bufs))) + +(defun helm-buffer-run-kill-buffers () + "Run kill buffer action from `helm-source-buffers-list'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-kill-marked-buffers))) +(put 'helm-buffer-run-kill-buffers 'helm-only t) + +(defun helm-buffer-run-grep () + "Run Grep action from `helm-source-buffers-list'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-grep-buffers))) +(put 'helm-buffer-run-grep 'helm-only t) + +(defun helm-buffer-run-zgrep () + "Run Grep action from `helm-source-buffers-list'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-zgrep-buffers))) +(put 'helm-buffer-run-zgrep 'helm-only t) + +(defun helm-buffer-run-query-replace-regexp () + "Run Query replace regexp action from `helm-source-buffers-list'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-buffer-query-replace-regexp))) +(put 'helm-buffer-run-query-replace-regexp 'helm-only t) + +(defun helm-buffer-run-query-replace () + "Run Query replace action from `helm-source-buffers-list'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-buffer-query-replace))) +(put 'helm-buffer-run-query-replace 'helm-only t) + +(defun helm-buffer-switch-other-window () + "Run switch to other window action from `helm-source-buffers-list'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-buffer-switch-buffers-other-window))) +(put 'helm-buffer-switch-other-window 'helm-only t) + +(defun helm-buffer-switch-other-frame () + "Run switch to other frame action from `helm-source-buffers-list'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'switch-to-buffer-other-frame))) +(put 'helm-buffer-switch-other-frame 'helm-only t) + +(defun helm-buffers-switch-to-buffer-new-tab () + "Run switch to buffer in other tab action from `helm-source-buffers-list'." + (interactive) + (cl-assert (fboundp 'tab-bar-mode) nil "Tab-bar-mode not available") + (with-helm-alive-p + (helm-exit-and-execute-action 'switch-to-buffer-other-tab))) +(put 'helm-buffers-switch-to-buffer-new-tab 'helm-only t) + +(defun helm-buffer-switch-buffers (_candidate) + "Switch to buffer candidates and replace current buffer. + +If more than one buffer marked switch to these buffers in separate windows. +If a prefix arg is given split windows vertically." + (let ((buffers (helm-marked-candidates))) + (helm-window-show-buffers buffers))) + +(defun helm-buffer-switch-buffers-other-window (_candidate) + "Switch to marked buffers in other windows." + (let ((buffers (helm-marked-candidates))) + (helm-window-show-buffers buffers t))) + +(defun helm-buffer-run-ediff () + "Run ediff action from `helm-source-buffers-list'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-ediff-marked-buffers))) +(put 'helm-buffer-run-ediff 'helm-only t) + +(defun helm-buffer-run-ediff-merge () + "Run ediff action from `helm-source-buffers-list'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-ediff-marked-buffers-merge))) +(put 'helm-buffer-run-ediff-merge 'helm-only t) + +(defun helm-buffers-persistent-kill-1 (buffer-or-name) + "Persistent action to kill buffer." + (let ((buf (get-buffer buffer-or-name)) helm-buf-or-cur) + (if (or (and (eql buf (get-buffer helm-current-buffer)) + (setq helm-buf-or-cur "helm-current-buffer")) + (and (eql buf (get-buffer helm-buffer)) + (setq helm-buf-or-cur "helm-buffer"))) + (progn + (message "Can't kill `%s' without quitting session" helm-buf-or-cur) + (sit-for 1)) + (kill-buffer buf) + (helm-delete-current-selection)))) + +(defun helm-buffers--quote-truncated-buffer (buffer) + (let ((bufname (and (bufferp buffer) + (buffer-name buffer)))) + (when (and bufname + (file-remote-p (with-current-buffer bufname + default-directory))) + (setq bufname (concat "@ " (helm-url-unhex-string bufname)))) + (when bufname + (regexp-quote + (if (and helm-buffer-max-length + helm-buffer-details-flag) + (helm-substring-by-width + bufname helm-buffer-max-length + "") + bufname))))) + +(defun helm-buffers-persistent-kill (_buffer) + (let ((marked (helm-marked-candidates)) + (sel (helm-get-selection))) + (unwind-protect + (cl-loop for b in marked + do (progn + ;; We need to preselect each marked because + ;; helm-buffers-persistent-kill is deleting + ;; current selection. + (helm-preselect + (format "^%s" + (helm-buffers--quote-truncated-buffer b))) + (helm-buffers-persistent-kill-1 b) + (message nil) + (helm--remove-marked-and-update-mode-line b))) + (with-helm-buffer + (setq helm-marked-candidates nil + helm-visible-mark-overlays nil)) + (helm-force-update (helm-buffers--quote-truncated-buffer sel))))) + +(defun helm-buffers-list-persistent-action (candidate) + (let ((current (window-buffer helm-persistent-action-display-window))) + (if (or (helm-follow-mode-p) + (eql current (get-buffer helm-current-buffer)) + (not (eql current (get-buffer candidate)))) + (switch-to-buffer candidate) + (if (and helm-persistent-action-display-window + (window-dedicated-p + (next-window helm-persistent-action-display-window 1))) + (delete-window helm-persistent-action-display-window) + (switch-to-buffer helm-current-buffer))))) + +(defun helm-ediff-marked-buffers (_candidate &optional merge) + "Ediff 2 marked buffers or CANDIDATE and `helm-current-buffer'. +With optional arg MERGE call `ediff-merge-buffers'." + (let ((lg-lst (length (helm-marked-candidates))) + buf1 buf2) + (cl-case lg-lst + (0 + (error "Error:You have to mark at least 1 buffer")) + (1 + (setq buf1 helm-current-buffer + buf2 (cl-first (helm-marked-candidates)))) + (2 + (setq buf1 (cl-first (helm-marked-candidates)) + buf2 (cl-second (helm-marked-candidates)))) + (t + (error "Error:Too many buffers marked!"))) + (if merge + (ediff-merge-buffers buf1 buf2) + (ediff-buffers buf1 buf2)))) + +(defun helm-ediff-marked-buffers-merge (candidate) + "Ediff merge `helm-current-buffer' with CANDIDATE. +See `helm-ediff-marked-buffers'." + (helm-ediff-marked-buffers candidate t)) + +(defun helm-multi-occur-as-action (_candidate) + "Multi occur action for `helm-source-buffers-list'. +Can be used by any source that list buffers." + (let ((helm-occur-always-search-in-current + (if helm-current-prefix-arg + (not helm-occur-always-search-in-current) + helm-occur-always-search-in-current)) + (buffers (helm-marked-candidates)) + (input (cl-loop for i in (split-string (or (buffer-local-value + 'helm-input-local + (get-buffer helm-buffer)) + helm-pattern) + " " t) + thereis (and (string-match "\\`@\\(.*\\)" i) + (match-string 1 i))))) + (helm-multi-occur-1 buffers input))) + +(defun helm-buffers-run-occur () + "Run `helm-multi-occur-as-action' by key." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-multi-occur-as-action))) +(put 'helm-buffers-run-occur 'helm-only t) + +(defun helm-buffers-toggle-show-hidden-buffers () + (interactive) + (with-helm-alive-p + (let ((filter-attrs (helm-attr 'filtered-candidate-transformer + helm-source-buffers-list))) + (if (memq 'helm-shadow-boring-buffers filter-attrs) + (helm-attrset 'filtered-candidate-transformer + (cons 'helm-skip-boring-buffers + (remove 'helm-shadow-boring-buffers + filter-attrs)) + helm-source-buffers-list) + (helm-attrset 'filtered-candidate-transformer + (cons 'helm-shadow-boring-buffers + (remove 'helm-skip-boring-buffers + filter-attrs)) + helm-source-buffers-list)) + (helm-force-update)))) +(put 'helm-buffers-toggle-show-hidden-buffers 'helm-only t) + +(defun helm-buffers-browse-project (buf) + "Browse project from buffer." + (with-current-buffer buf + (helm-browse-project helm-current-prefix-arg))) + +(defun helm-buffers-run-browse-project () + "Run `helm-buffers-browse-project' from key." + (interactive) + (with-helm-alive-p + (if helm-buffers-in-project-p + (user-error "You are already browsing this project") + (helm-exit-and-execute-action 'helm-buffers-browse-project)))) + +;;; Candidate Transformers +;; +;; +(defun helm-skip-boring-buffers (buffers _source) + (helm-skip-entries buffers + helm-boring-buffer-regexp-list + helm-white-buffer-regexp-list)) + +(defun helm-shadow-boring-buffers (buffers _source) + "Buffers matching `helm-boring-buffer-regexp' will be +displayed with the `file-name-shadow' face if available." + (helm-shadow-entries buffers helm-boring-buffer-regexp-list)) + + +;;;###autoload +(defun helm-buffers-list () + "Preconfigured `helm' to list buffers." + (interactive) + (unless helm-source-buffers-list + (setq helm-source-buffers-list + (helm-make-source "Buffers" 'helm-source-buffers))) + (helm :sources '(helm-source-buffers-list + helm-source-ido-virtual-buffers + helm-source-buffer-not-found) + :buffer "*helm buffers*" + :keymap helm-buffer-map + :truncate-lines helm-buffers-truncate-lines + :left-margin-width helm-buffers-left-margin-width)) + +;;;###autoload +(defun helm-mini () + "Preconfigured `helm' displaying `helm-mini-default-sources'." + (interactive) + (require 'helm-x-files) + (unless helm-source-buffers-list + (setq helm-source-buffers-list + (helm-make-source "Buffers" 'helm-source-buffers))) + (helm :sources helm-mini-default-sources + :buffer "*helm mini*" + :ff-transformer-show-only-basename nil + :truncate-lines helm-buffers-truncate-lines + :left-margin-width helm-buffers-left-margin-width)) + +(defun helm-quit-and-helm-mini () + "Drop into `helm-mini' from `helm'." + (interactive) + (with-helm-alive-p + (helm-run-after-exit 'helm-mini))) + +(provide 'helm-buffers) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-buffers.el ends here diff --git a/elpa/helm-20191031.839/helm-color.el b/elpa/helm-20191031.839/helm-color.el new file mode 100644 index 00000000..a962796a --- /dev/null +++ b/elpa/helm-20191031.839/helm-color.el @@ -0,0 +1,170 @@ +;;; helm-color.el --- colors and faces -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: +(require 'cl-lib) +(require 'helm) +(require 'helm-help) +(require 'helm-elisp) + +;;; Customize Face +;; +;; +(defun helm-custom-faces-init () + "Initialize buffer for `helm-source-customize-face'." + (unless (helm-candidate-buffer) + (save-selected-window + (list-faces-display) + (message nil)) + (helm-init-candidates-in-buffer + 'global + (with-current-buffer (get-buffer "*Faces*") + (buffer-substring + (next-single-char-property-change (point-min) 'face) + (point-max)))) + (kill-buffer "*Faces*"))) + +(defvar helm-source-customize-face + (helm-build-in-buffer-source "Customize Face" + :init 'helm-custom-faces-init + :get-line 'buffer-substring + :persistent-action (lambda (candidate) + (helm-elisp--persistent-help + (intern (car (split-string candidate))) + 'helm-describe-face)) + :persistent-help "Describe face" + :action '(("Customize" + . (lambda (line) + (customize-face (intern (car (split-string line)))))) + ("Copy name" + . (lambda (line) + (kill-new (car (split-string line " " t))))))) + "See (info \"(emacs)Faces\")") + +;;; Colors browser +;; +;; +(defun helm-colors-init () + (unless (helm-candidate-buffer) + (save-selected-window + (list-colors-display) + (message nil)) + (helm-init-candidates-in-buffer + 'global + (with-current-buffer (get-buffer "*Colors*") + (buffer-string))) + (kill-buffer "*Colors*"))) + +(defun helm-color-insert-name (candidate) + (with-helm-current-buffer + (insert (helm-colors-get-name candidate)))) + +(defun helm-color-kill-name (candidate) + (kill-new (helm-colors-get-name candidate))) + +(defun helm-color-insert-rgb (candidate) + (with-helm-current-buffer + (insert (helm-colors-get-rgb candidate)))) + +(defun helm-color-kill-rgb (candidate) + (kill-new (helm-colors-get-rgb candidate))) + +(defun helm-color-run-insert-name () + "Insert name of color from `helm-source-colors'" + (interactive) + (with-helm-alive-p (helm-exit-and-execute-action 'helm-color-insert-name))) +(put 'helm-color-run-insert-name 'helm-only t) + +(defun helm-color-run-kill-name () + "Kill name of color from `helm-source-colors'" + (interactive) + (with-helm-alive-p (helm-exit-and-execute-action 'helm-color-kill-name))) +(put 'helm-color-run-kill-name 'helm-only t) + +(defun helm-color-run-insert-rgb () + "Insert RGB of color from `helm-source-colors'" + (interactive) + (with-helm-alive-p (helm-exit-and-execute-action 'helm-color-insert-rgb))) +(put 'helm-color-run-insert-rgb 'helm-only t) + +(defun helm-color-run-kill-rgb () + "Kill RGB of color from `helm-source-colors'" + (interactive) + (with-helm-alive-p (helm-exit-and-execute-action 'helm-color-kill-rgb))) +(put 'helm-color-run-kill-rgb 'helm-only t) + +(defvar helm-color-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "C-c n") 'helm-color-run-insert-name) + (define-key map (kbd "C-c N") 'helm-color-run-kill-name) + (define-key map (kbd "C-c r") 'helm-color-run-insert-rgb) + (define-key map (kbd "C-c R") 'helm-color-run-kill-rgb) + map)) + +(defvar helm-source-colors + (helm-build-in-buffer-source "Colors" + :init 'helm-colors-init + :get-line 'buffer-substring + :keymap helm-color-map + :persistent-help "Kill entry in RGB format." + :persistent-action 'helm-color-kill-rgb + :help-message 'helm-colors-help-message + :action + '(("Copy Name (C-c N)" . helm-color-kill-name) + ("Copy RGB (C-c R)" . helm-color-kill-rgb) + ("Insert Name (C-c n)" . helm-color-insert-name) + ("Insert RGB (C-c r)" . helm-color-insert-rgb)))) + +(defun helm-colors-get-name (candidate) + "Get color name." + (replace-regexp-in-string + " " "" + (with-temp-buffer + (insert (capitalize candidate)) + (goto-char (point-min)) + (search-forward-regexp "\\s-\\{2,\\}") + (delete-region (point) (point-max)) + (buffer-string)))) + +(defun helm-colors-get-rgb (candidate) + "Get color RGB." + (replace-regexp-in-string + " " "" + (with-temp-buffer + (insert (capitalize candidate)) + (goto-char (point-max)) + (search-backward-regexp "\\s-\\{2,\\}") + (delete-region (point) (point-min)) + (buffer-string)))) + +;;;###autoload +(defun helm-colors () + "Preconfigured `helm' for color." + (interactive) + (helm :sources '(helm-source-colors helm-source-customize-face) + :buffer "*helm colors*")) + +(provide 'helm-color) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-color.el ends here diff --git a/elpa/helm-20191031.839/helm-comint.el b/elpa/helm-20191031.839/helm-comint.el new file mode 100644 index 00000000..953d8a76 --- /dev/null +++ b/elpa/helm-20191031.839/helm-comint.el @@ -0,0 +1,219 @@ +;;; helm-comint.el --- Comint prompt navigation for helm. -*- lexical-binding: t -*- + +;; Copyright (C) 2019 Pierre Neidhardt + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Commentary: +;; +;; You can bind this as follows in .emacs: +;; +;; (add-hook 'comint-mode-hook +;; (lambda () +;; (define-key comint-mode-map (kbd "M-s f") 'helm-comint-prompts-all))) + +;;; Code: +(require 'cl-lib) +(require 'helm) +(require 'helm-lib) +(require 'helm-help) +(require 'helm-elisp) + +;;; Comint prompts +;; +(defface helm-comint-prompts-promptidx + '((t (:foreground "cyan"))) + "Face used to highlight comint prompt index." + :group 'helm-comint-faces) + +(defface helm-comint-prompts-buffer-name + '((t (:foreground "green"))) + "Face used to highlight comint buffer name." + :group 'helm-comint-faces) + +(defcustom helm-comint-prompts-promptidx-p t + "Show prompt number." + :group 'helm-comint + :type 'boolean) + +(defcustom helm-comint-mode-list '(comint-mode slime-repl-mode) + "Supported modes for prompt navigation. +Derived modes (e.g. Geiser's REPL) are automatically supported." + :group 'helm-comint + :type '(repeat (choice symbol))) + +(defcustom helm-comint-max-offset 400 + "Max number of chars displayed per candidate in comint-input-ring browser. +When `t', don't truncate candidate, show all. +By default it is approximatively the number of bits contained in five lines +of 80 chars each i.e 80*5. +Note that if you set this to nil multiline will be disabled, i.e you +will not have anymore separators between candidates." + :type '(choice (const :tag "Disabled" t) + (integer :tag "Max candidate offset")) + :group 'helm-misc) + +(defvar helm-comint-prompts-keymap + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "C-c o") 'helm-comint-prompts-other-window) + (define-key map (kbd "C-c C-o") 'helm-comint-prompts-other-frame) + map) + "Keymap for `helm-comint-prompt-all'.") + +(defun helm-comint-prompts-list (mode &optional buffer) + "List the prompts in BUFFER in mode MODE. + +Return a list of (\"prompt\" (point) (buffer-name) prompt-index)) +e.g. (\"ls\" 162 \"*shell*\" 3). +If BUFFER is nil, use current buffer." + (with-current-buffer (or buffer (current-buffer)) + (when (derived-mode-p mode) + (save-excursion + (goto-char (point-min)) + (let (result (count 1)) + (save-mark-and-excursion + (helm-awhile (and (not (eobp)) (comint-next-prompt 1)) + (push (list (buffer-substring-no-properties + it (point-at-eol)) + it (buffer-name) count) + result) + (setq count (1+ count)))) + (nreverse result)))))) + +(defun helm-comint-prompts-list-all (mode) + "List the prompts of all buffers in mode MODE. +See `helm-comint-prompts-list'." + (cl-loop for b in (buffer-list) + append (helm-comint-prompts-list mode b))) + +(defun helm-comint-prompts-transformer (candidates &optional all) + ;; ("ls" 162 "*shell*" 3) => ("*shell*:3:ls" . ("ls" 162 "*shell*" 3)) + (cl-loop for (prt pos buf id) in candidates + collect `(,(concat + (when all + (concat (propertize + buf + 'face 'helm-comint-prompts-buffer-name) + ":")) + (when helm-comint-prompts-promptidx-p + (concat (propertize + (number-to-string id) + 'face 'helm-comint-prompts-promptidx) + ":")) + prt) + . ,(list prt pos buf id)))) + +(defun helm-comint-prompts-all-transformer (candidates) + (helm-comint-prompts-transformer candidates t)) + +(cl-defun helm-comint-prompts-goto (candidate &optional (action 'switch-to-buffer)) + ;; Candidate format: ("ls" 162 "*shell*" 3) + (let ((buf (nth 2 candidate))) + (unless (and (string= (buffer-name) buf) + (eq action 'switch-to-buffer)) + (funcall action buf)) + (goto-char (nth 1 candidate)) + (recenter))) + +(defun helm-comint-prompts-goto-other-window (candidate) + (helm-comint-prompts-goto candidate 'switch-to-buffer-other-window)) + +(defun helm-comint-prompts-goto-other-frame (candidate) + (helm-comint-prompts-goto candidate 'switch-to-buffer-other-frame)) + +(defun helm-comint-prompts-other-window () + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-comint-prompts-goto-other-window))) +(put 'helm-comint-prompts-other-window 'helm-only t) + +(defun helm-comint-prompts-other-frame () + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-comint-prompts-goto-other-frame))) +(put 'helm-comint-prompts-other-frame 'helm-only t) + +;;;###autoload +(defun helm-comint-prompts () + "Pre-configured `helm' to browse the prompts of the current comint buffer." + (interactive) + (if (apply 'derived-mode-p helm-comint-mode-list) + (helm :sources + (helm-build-sync-source "Comint prompts" + :candidates (helm-comint-prompts-list major-mode) + :candidate-transformer 'helm-comint-prompts-transformer + :action '(("Go to prompt" . helm-comint-prompts-goto))) + :buffer "*helm comint prompts*") + (message "Current buffer is not a comint buffer"))) + +;;;###autoload +(defun helm-comint-prompts-all () + "Pre-configured `helm' to browse the prompts of all comint sessions." + (interactive) + (if (apply 'derived-mode-p helm-comint-mode-list) + (helm :sources + (helm-build-sync-source "All comint prompts" + :candidates (helm-comint-prompts-list-all major-mode) + :candidate-transformer 'helm-comint-prompts-all-transformer + :action (quote (("Go to prompt" . helm-comint-prompts-goto) + ("Go to prompt in other window `C-c o`" . + helm-comint-prompts-goto-other-window) + ("Go to prompt in other frame `C-c C-o`" . + helm-comint-prompts-goto-other-frame))) + :keymap helm-comint-prompts-keymap) + :buffer "*helm comint all prompts*") + (message "Current buffer is not a comint buffer"))) + +;;; Comint history +;; +;; +(defun helm-comint-input-ring-action (candidate) + "Default action for comint history." + (with-helm-current-buffer + (delete-region (comint-line-beginning-position) (point-max)) + (insert candidate))) + +(defvar helm-source-comint-input-ring + (helm-build-sync-source "Comint history" + :candidates (lambda () + (with-helm-current-buffer + (cl-loop for elm in (ring-elements comint-input-ring) + unless (string= elm "") + collect elm))) + :action 'helm-comint-input-ring-action + ;; Multiline does not work for `shell' because of an Emacs bug. + ;; It works in other REPLs like Geiser. + :multiline 'helm-comint-max-offset) + "Source that provides Helm completion against `comint-input-ring'.") + +;;;###autoload +(defun helm-comint-input-ring () + "Preconfigured `helm' that provide completion of `comint' history." + (interactive) + (when (derived-mode-p 'comint-mode) + (helm :sources 'helm-source-comint-input-ring + :input (buffer-substring-no-properties (comint-line-beginning-position) + (point-at-eol)) + :buffer "*helm comint history*"))) + +(provide 'helm-comint) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-comint.el ends here diff --git a/elpa/helm-20191031.839/helm-command.el b/elpa/helm-20191031.839/helm-command.el new file mode 100644 index 00000000..54aae483 --- /dev/null +++ b/elpa/helm-20191031.839/helm-command.el @@ -0,0 +1,308 @@ +;;; helm-command.el --- Helm execute-exended-command. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'cl-lib) +(require 'helm) +(require 'helm-help) +(require 'helm-mode) +(require 'helm-elisp) + + +(defgroup helm-command nil + "Emacs command related Applications and libraries for Helm." + :group 'helm) + +(defcustom helm-M-x-requires-pattern 0 + "Value of requires-pattern for `helm-M-x'. +Show all candidates on startup when 0 (default)." + :group 'helm-command + :type 'boolean) + +(defcustom helm-M-x-always-save-history nil + "`helm-M-x' Save command in `extended-command-history' even when it fail." + :group 'helm-command + :type 'boolean) + +(defcustom helm-M-x-reverse-history nil + "The history source of `helm-M-x' appear in second position when non--nil." + :group 'helm-command + :type 'boolean) + +(defcustom helm-M-x-fuzzy-match nil + "Enable fuzzy matching in `helm-M-x' when non--nil." + :group 'helm-command + :type 'boolean) + +(defcustom helm-M-x-default-sort-fn #'helm-M-x-fuzzy-sort-candidates + "Default sort function for `helm-M-x'. + +It should sort against REAL value of candidates. + +It is used only when `helm-M-x-fuzzy-match' is enabled." + :group 'helm-command + :type 'function) + +;;; Faces +;; +;; +(defgroup helm-command-faces nil + "Customize the appearance of helm-command." + :prefix "helm-" + :group 'helm-command + :group 'helm-faces) + +(defface helm-M-x-key '((t (:foreground "orange" :underline t))) + "Face used in helm-M-x to show keybinding." + :group 'helm-command-faces) + + +(defvar helm-M-x-input-history nil) +(defvar helm-M-x-prefix-argument nil + "Prefix argument before calling `helm-M-x'.") + + +(defun helm-M-x-get-major-mode-command-alist (mode-map) + "Return alist of MODE-MAP." + (when mode-map + (cl-loop for key being the key-seqs of mode-map using (key-bindings com) + for str-key = (key-description key) + for ismenu = (string-match "" str-key) + unless ismenu collect (cons str-key com)))) + +(defun helm-get-mode-map-from-mode (mode) + "Guess the mode-map name according to MODE. +Some modes don't use conventional mode-map name +so we need to guess mode-map name. e.g python-mode ==> py-mode-map. +Return nil if no mode-map found." + (cl-loop ;; Start with a conventional mode-map name. + with mode-map = (intern-soft (format "%s-map" mode)) + with mode-string = (symbol-name mode) + with mode-name = (replace-regexp-in-string "-mode" "" mode-string) + while (not mode-map) + for count downfrom (length mode-name) + ;; Return when no result after parsing entire string. + when (eq count 0) return nil + for sub-name = (substring mode-name 0 count) + do (setq mode-map (intern-soft (format "%s-map" (concat sub-name "-mode")))) + finally return mode-map)) + +(defun helm-M-x-current-mode-map-alist () + "Return mode-map alist of current `major-mode'." + (let ((map-sym (helm-get-mode-map-from-mode major-mode))) + (when (and map-sym (boundp map-sym)) + (helm-M-x-get-major-mode-command-alist (symbol-value map-sym))))) + + +(defun helm-M-x-transformer-1 (candidates &optional sort) + "Transformer function to show bindings in emacs commands. +Show global bindings and local bindings according to current `major-mode'. +If SORT is non nil sort list with `helm-generic-sort-fn'. +Note that SORT should not be used when fuzzy matching because +fuzzy matching is running its own sort function with a different algorithm." + (with-helm-current-buffer + (cl-loop with local-map = (helm-M-x-current-mode-map-alist) + for cand in candidates + for local-key = (car (rassq cand local-map)) + for key = (substitute-command-keys (format "\\[%s]" cand)) + unless (get (intern (if (consp cand) (car cand) cand)) 'helm-only) + collect + (cons (cond ((and (string-match "^M-x" key) local-key) + (format "%s (%s)" + cand (propertize + local-key + 'face 'helm-M-x-key))) + ((string-match "^M-x" key) cand) + (t (format "%s (%s)" + cand (propertize + key + 'face 'helm-M-x-key)))) + cand) + into ls + finally return + (if sort (sort ls #'helm-generic-sort-fn) ls)))) + +(defun helm-M-x-transformer (candidates _source) + "Transformer function for `helm-M-x' candidates." + (helm-M-x-transformer-1 candidates (null helm--in-fuzzy))) + +(defun helm-M-x-transformer-hist (candidates _source) + "Transformer function for `helm-M-x' candidates." + (helm-M-x-transformer-1 candidates)) + +(defun helm-M-x--notify-prefix-arg () + ;; Notify a prefix-arg set AFTER calling M-x. + (when prefix-arg + (with-helm-window + (helm-display-mode-line (helm-get-current-source) 'force)))) + +(defun helm-cmd--get-current-function-name () + (save-excursion + (beginning-of-defun) + (cadr (split-string (buffer-substring-no-properties + (point-at-bol) (point-at-eol)))))) + +(defun helm-cmd--get-preconfigured-commands (&optional dir) + (let* ((helm-dir (or dir (helm-basedir (locate-library "helm")))) + (helm-autoload-file (expand-file-name "helm-autoloads.el" helm-dir)) + results) + (when (file-exists-p helm-autoload-file) + (with-temp-buffer + (insert-file-contents helm-autoload-file) + (while (re-search-forward "Preconfigured" nil t) + (push (substring (helm-cmd--get-current-function-name) 1) results)))) + results)) + +(defvar helm-M-x-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-comp-read-map) + (define-key map (kbd "C-u") nil) + (define-key map (kbd "C-u") 'helm-M-x-universal-argument) + map)) + +(defun helm-M-x-universal-argument () + "Same as `universal-argument' but for `helm-M-x'." + (interactive) + (if helm-M-x-prefix-argument + (progn (setq helm-M-x-prefix-argument nil) + (let ((inhibit-read-only t)) + (with-selected-window (minibuffer-window) + (save-excursion + (goto-char (point-min)) + (delete-char (- (minibuffer-prompt-width) (length "M-x ")))))) + (message "Initial prefix arg disabled")) + (setq prefix-arg (list 4)) + (universal-argument--mode))) +(put 'helm-M-x-universal-argument 'helm-only t) + +(defun helm-M-x-fuzzy-sort-candidates (candidates _source) + (helm-fuzzy-matching-default-sort-fn-1 candidates t)) + +(defun helm-M-x-read-extended-command (&optional collection history) + "Read command name to invoke in `helm-M-x'. +Helm completion is not provided when executing or defining +kbd macros. +Optional arg COLLECTION is to allow using another COLLECTION +than the default which is OBARRAY." + (if (or defining-kbd-macro executing-kbd-macro) + (if helm-mode + (unwind-protect + (progn + (helm-mode -1) + (read-extended-command)) + (helm-mode 1)) + (read-extended-command)) + (let* ((helm-fuzzy-sort-fn helm-M-x-default-sort-fn) + (helm--mode-line-display-prefarg t) + (tm (run-at-time 1 0.1 'helm-M-x--notify-prefix-arg)) + (helm-move-selection-after-hook + (cons (lambda () (setq current-prefix-arg nil)) + helm-move-selection-after-hook))) + (setq extended-command-history + (cl-loop for c in extended-command-history + when (and c (commandp (intern c))) + do (set-text-properties 0 (length c) nil c) + and collect c)) + (unwind-protect + (progn + (setq current-prefix-arg nil) + (helm-comp-read + (concat (cond + ((eq helm-M-x-prefix-argument '-) "- ") + ((and (consp helm-M-x-prefix-argument) + (eq (car helm-M-x-prefix-argument) 4)) "C-u ") + ((and (consp helm-M-x-prefix-argument) + (integerp (car helm-M-x-prefix-argument))) + (format "%d " (car helm-M-x-prefix-argument))) + ((integerp helm-M-x-prefix-argument) + (format "%d " helm-M-x-prefix-argument))) + "M-x ") + (or collection obarray) + :test 'commandp + :requires-pattern helm-M-x-requires-pattern + :name "Emacs Commands" + :buffer "*helm M-x*" + :persistent-action (lambda (candidate) + (helm-elisp--persistent-help + candidate 'helm-describe-function)) + :persistent-help "Describe this command" + :history (or history extended-command-history) + :reverse-history helm-M-x-reverse-history + :input-history 'helm-M-x-input-history + :del-input nil + :help-message 'helm-M-x-help-message + :group 'helm-command + :keymap helm-M-x-map + :must-match t + :match-part (lambda (c) (car (split-string c))) + :fuzzy helm-M-x-fuzzy-match + :nomark t + :candidates-in-buffer t + :fc-transformer 'helm-M-x-transformer + :hist-fc-transformer 'helm-M-x-transformer-hist)) + (cancel-timer tm) + (setq helm--mode-line-display-prefarg nil))))) + +;;;###autoload +(defun helm-M-x (_arg &optional command-name) + "Preconfigured `helm' for Emacs commands. +It is `helm' replacement of regular `M-x' `execute-extended-command'. + +Unlike regular `M-x' emacs vanilla `execute-extended-command' command, +the prefix args if needed, can be passed AFTER starting `helm-M-x'. +When a prefix arg is passed BEFORE starting `helm-M-x', the first `C-u' +while in `helm-M-x' session will disable it. + +You can get help on each command by persistent action." + (interactive + (progn + (setq helm-M-x-prefix-argument current-prefix-arg) + (list current-prefix-arg (helm-M-x-read-extended-command)))) + (when (stringp command-name) + (unless (string= command-name "") + (let ((sym-com (and (stringp command-name) (intern-soft command-name)))) + (when sym-com + ;; Avoid having `this-command' set to *exit-minibuffer. + (setq this-command sym-com + ;; Handle C-x z (repeat) Issue #322 + real-this-command sym-com) + ;; If helm-M-x is called with regular emacs completion (kmacro) + ;; use the value of arg otherwise use helm-current-prefix-arg. + (let ((prefix-arg (or helm-current-prefix-arg helm-M-x-prefix-argument))) + (cl-flet ((save-hist (command) + (setq extended-command-history + (cons command (delete command extended-command-history))))) + (condition-case-unless-debug err + (progn + (command-execute sym-com 'record) + (save-hist command-name)) + (error + (when helm-M-x-always-save-history + (save-hist command-name)) + (signal (car err) (cdr err))))))))))) +(put 'helm-M-x 'interactive-only 'command-execute) + +(provide 'helm-command) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-command.el ends here diff --git a/elpa/helm-20191031.839/helm-config.el b/elpa/helm-20191031.839/helm-config.el new file mode 100644 index 00000000..36107538 --- /dev/null +++ b/elpa/helm-20191031.839/helm-config.el @@ -0,0 +1,172 @@ +;;; helm-config.el --- Applications library for `helm.el' -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + + +;;; Require +;; +;; +(declare-function async-bytecomp-package-mode "ext:async-bytecomp.el") +(when (require 'async-bytecomp nil t) + (and (fboundp 'async-bytecomp-package-mode) + (async-bytecomp-package-mode 1))) + + +(defgroup helm-config nil + "Various configurations for Helm." + :group 'helm) + +(defcustom helm-command-prefix-key "C-x c" + "The key `helm-command-prefix' is bound to in the global map." + :type '(choice (string :tag "Key") (const :tag "no binding")) + :group 'helm-config + :set + (lambda (var key) + (when (and (boundp var) (symbol-value var)) + (define-key (current-global-map) + (read-kbd-macro (symbol-value var)) nil)) + (when key + (define-key (current-global-map) + (read-kbd-macro key) 'helm-command-prefix)) + (set var key))) + +(defcustom helm-minibuffer-history-key "C-r" + "The key `helm-minibuffer-history' is bound to in minibuffer local maps." + :type '(choice (string :tag "Key") (const :tag "no binding")) + :group 'helm-config + :set + (lambda (var key) + (cl-dolist (map '(minibuffer-local-completion-map + minibuffer-local-filename-completion-map + minibuffer-local-filename-must-match-map ; Emacs 23.1.+ + minibuffer-local-isearch-map + minibuffer-local-map + minibuffer-local-must-match-filename-map ; Older Emacsen + minibuffer-local-must-match-map + minibuffer-local-ns-map)) + (when (and (boundp map) (keymapp (symbol-value map))) + (when (and (boundp var) (symbol-value var)) + (define-key (symbol-value map) + (read-kbd-macro (symbol-value var)) nil)) + (when key + (define-key (symbol-value map) + (read-kbd-macro key) 'helm-minibuffer-history)))) + (set var key))) + +;;; Command Keymap +;; +;; +(defvar helm-command-map + (let ((map (make-sparse-keymap))) + (define-key map (kbd "a") 'helm-apropos) + (define-key map (kbd "e") 'helm-etags-select) + (define-key map (kbd "l") 'helm-locate) + (define-key map (kbd "s") 'helm-surfraw) + (define-key map (kbd "r") 'helm-regexp) + (define-key map (kbd "m") 'helm-man-woman) + (define-key map (kbd "t") 'helm-top) + (define-key map (kbd "/") 'helm-find) + (define-key map (kbd "i") 'helm-semantic-or-imenu) + (define-key map (kbd "I") 'helm-imenu-in-all-buffers) + (define-key map (kbd "") 'helm-lisp-completion-at-point) + (define-key map (kbd "p") 'helm-list-emacs-process) + (define-key map (kbd "C-x r b") 'helm-filtered-bookmarks) + (define-key map (kbd "M-y") 'helm-show-kill-ring) + (define-key map (kbd "C-c ") 'helm-all-mark-rings) + (define-key map (kbd "C-x C-f") 'helm-find-files) + (define-key map (kbd "f") 'helm-multi-files) + (define-key map (kbd "C-:") 'helm-eval-expression-with-eldoc) + (define-key map (kbd "C-,") 'helm-calcul-expression) + (define-key map (kbd "M-x") 'helm-M-x) + (define-key map (kbd "M-s o") 'helm-occur) + (define-key map (kbd "M-g a") 'helm-do-grep-ag) + (define-key map (kbd "c") 'helm-colors) + (define-key map (kbd "F") 'helm-select-xfont) + (define-key map (kbd "8") 'helm-ucs) + (define-key map (kbd "C-c f") 'helm-recentf) + (define-key map (kbd "C-c g") 'helm-google-suggest) + (define-key map (kbd "h i") 'helm-info-at-point) + (define-key map (kbd "h r") 'helm-info-emacs) + (define-key map (kbd "h g") 'helm-info-gnus) + (define-key map (kbd "h h") 'helm-documentation) + (define-key map (kbd "C-x C-b") 'helm-buffers-list) + (define-key map (kbd "C-x r i") 'helm-register) + (define-key map (kbd "C-c C-x") 'helm-run-external-command) + (define-key map (kbd "b") 'helm-resume) + (define-key map (kbd "M-g i") 'helm-gid) + (define-key map (kbd "@") 'helm-list-elisp-packages) + map)) + +;; Don't override the keymap we just defined with an empty +;; keymap. This also protect bindings changed by the user. +(defvar helm-command-prefix) +(define-prefix-command 'helm-command-prefix) +(fset 'helm-command-prefix helm-command-map) +(setq helm-command-prefix helm-command-map) + + +;;; Menu + +(require 'helm-easymenu) + + +;;;###autoload +(defun helm-configuration () + "Customize `helm'." + (interactive) + (customize-group "helm")) + + +;;; Fontlock +(cl-dolist (mode '(emacs-lisp-mode lisp-interaction-mode)) + (font-lock-add-keywords + mode + '(("(\\<\\(with-helm-after-update-hook\\)\\>" 1 font-lock-keyword-face) + ("(\\<\\(with-helm-temp-hook\\)\\>" 1 font-lock-keyword-face) + ("(\\<\\(with-helm-window\\)\\>" 1 font-lock-keyword-face) + ("(\\<\\(with-helm-quittable\\)\\>" 1 font-lock-keyword-face) + ("(\\<\\(with-helm-current-buffer\\)\\>" 1 font-lock-keyword-face) + ("(\\<\\(with-helm-buffer\\)\\>" 1 font-lock-keyword-face) + ("(\\<\\(with-helm-show-completion\\)\\>" 1 font-lock-keyword-face) + ("(\\<\\(with-helm-default-directory\\)\\>" 1 font-lock-keyword-face) + ("(\\<\\(with-helm-restore-variables\\)\\>" 1 font-lock-keyword-face) + ("(\\<\\(helm-multi-key-defun\\)\\>" 1 font-lock-keyword-face) + ("(\\<\\(helm-while-no-input\\)\\>" 1 font-lock-keyword-face) + ("(\\<\\(helm-aif\\)\\>" 1 font-lock-keyword-face) + ("(\\<\\(helm-awhile\\)\\>" 1 font-lock-keyword-face) + ("(\\<\\(helm-acond\\)\\>" 1 font-lock-keyword-face) + ("(\\<\\(helm-aand\\)\\>" 1 font-lock-keyword-face) + ("(\\<\\(helm-with-gensyms\\)\\>" 1 font-lock-keyword-face) + ("(\\<\\(helm-read-answer\\)\\>" 1 font-lock-keyword-face)))) + + +;;; Load the autoload file +;; It should have been generated either by +;; package.el or the make file. + +(load "helm-autoloads" nil t) + +(provide 'helm-config) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-config.el ends here diff --git a/elpa/helm-20191031.839/helm-dabbrev.el b/elpa/helm-20191031.839/helm-dabbrev.el new file mode 100644 index 00000000..6adce190 --- /dev/null +++ b/elpa/helm-20191031.839/helm-dabbrev.el @@ -0,0 +1,388 @@ +;;; helm-dabbrev.el --- Helm implementation of dabbrev. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'helm) +(require 'helm-lib) +(require 'helm-help) +(require 'helm-elisp) ; For show-completion. + +(defgroup helm-dabbrev nil + "Dabbrev related Applications and libraries for Helm." + :group 'helm) + +(defcustom helm-dabbrev-always-search-all t + "Always search in all buffers when non--nil. +Note that even if nil, a search in all buffers +will occur if the length of candidates is <= than +`helm-dabbrev-max-length-result'." + :group 'helm-dabbrev + :type 'boolean) + +(defcustom helm-dabbrev-candidates-number-limit 1000 + "Maximum number of candidates to collect. + +Higher this number is, slower the computation of candidates will be. +You can use safely a higher value with emacs-26+. +Note that this have nothing to do with `helm-candidate-number-limit'." + :group 'helm-dabbrev + :type 'integer) + +(defcustom helm-dabbrev-ignored-buffers-regexps + '("\\*helm" "\\*Messages" "\\*Echo Area" "\\*Buffer List") + "List of regexps matching names of buffers that helm-dabbrev should not check." + :group 'helm-dabbrev + :type '(repeat regexp)) + +(defcustom helm-dabbrev-related-buffer-fn #'helm-dabbrev--same-major-mode-p + "A function that decide if a buffer to search in is related to `current-buffer'. +This is actually determined by comparing `major-mode' of the buffer to search +and the `current-buffer'. +The function take one arg, the buffer which is current, look at +`helm-dabbrev--same-major-mode-p' for example. + +When nil all buffers are considered related to `current-buffer'." + :group 'helm-dabbrev + :type 'function) + +(defcustom helm-dabbrev-major-mode-assoc nil + "Major mode association alist. +This allow helm-dabbrev searching in buffers with the associated `major-mode'. +e.g \(emacs-lisp-mode . lisp-interaction-mode\) +will allow searching in the lisp-interaction-mode buffer when `current-buffer' +is an `emacs-lisp-mode' buffer and vice versa i.e +no need to provide \(lisp-interaction-mode . emacs-lisp-mode\) association. + +When nil check is the searched buffer have same `major-mode' +than the `current-buffer'. +This have no effect when `helm-dabbrev-related-buffer-fn' is nil or of course +bound to a function that doesn't handle this var." + :type '(alist :key-type symbol :value-type symbol) + :group 'helm-dabbrev) + +(defcustom helm-dabbrev-lineno-around 30 + "Search first in this number of lines before an after point." + :group 'helm-dabbrev + :type 'integer) + +(defcustom helm-dabbrev-cycle-threshold 5 + "Number of time helm-dabbrev cycle before displaying helm completion. +When nil or 0 disable cycling." + :group 'helm-dabbrev + :type '(choice (const :tag "Cycling disabled" nil) integer)) + +(defcustom helm-dabbrev-case-fold-search 'smart + "Set `case-fold-search' in `helm-dabbrev'. +Same as `helm-case-fold-search' but for `helm-dabbrev'. +Note that this is not affecting searching in helm buffer, +but the initial search for all candidates in buffer(s)." + :group 'helm-dabbrev + :type '(choice (const :tag "Ignore case" t) + (const :tag "Respect case" nil) + (other :tag "Smart" 'smart))) + +(defcustom helm-dabbrev-use-thread nil + "[EXPERIMENTAL] Compute candidates asynchronously (partially) when non nil. + +The idea is to compute candidates while cycling the first ones, so +this is available only if `helm-dabbrev-cycle-threshold' is not 0 or +nil, also it is available only on emacs-26+ (needs threads). + +This is reasonably working when you don't have to complete a huge list +of candidates, otherwise you will have a small delay after the first cycle +because thread is released unexpectedly when helm-dabbrev exit after +first insertion. + +IOW keep `helm-dabbrev-candidates-number-limit' to a reasonable +value (I don't!) and give enough prefix before completing e.g. for +completing \"helm-dabbrev\" use \"helm-d\" and not \"he\" if you want +to use this." + :group 'helm-dabbrev + :type 'boolean) + +(defvaralias 'helm-dabbrev--regexp 'helm-dabbrev-separator-regexp) +(make-obsolete-variable 'helm-dabbrev--regexp + 'helm-dabbrev-separator-regexp "2.8.3") +;; Check for beginning of line should happen last (^\n\\|^). +(defvar helm-dabbrev-separator-regexp + "\\s-\\|\t\\|[(\\[\\{\"'`=<$;,@.#+]\\|\\s\\\\|^\n\\|^" + "Regexp matching the start of a dabbrev candidate.") + + +(defvar helm-dabbrev-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "M-/") 'helm-next-line) + (define-key map (kbd "M-:") 'helm-previous-line) + map)) + +;; Internal +(defvar helm-dabbrev--cache nil) +(defvar helm-dabbrev--data nil) +(cl-defstruct helm-dabbrev-info dabbrev limits iterator) +(defvar helm-dabbrev--already-tried nil) +(defvar helm-dabbrev--current-thread nil) + + +(defun helm-dabbrev--buffer-list () + (cl-loop for buf in (buffer-list) + unless (cl-loop for r in helm-dabbrev-ignored-buffers-regexps + thereis (string-match r (buffer-name buf))) + collect buf)) + +(defun helm-dabbrev--same-major-mode-p (start-buffer) + "Decide if current-buffer is related to START-BUFFER." + (helm-same-major-mode-p start-buffer helm-dabbrev-major-mode-assoc)) + +(defun helm-dabbrev--collect (str limit ignore-case all) + (let* ((case-fold-search ignore-case) + (buffer1 (current-buffer)) ; start buffer. + (minibuf (minibufferp buffer1)) + result pos-before pos-after + (search-and-store + (lambda (pattern direction) + (while (and (<= (length result) limit) + (cl-case direction + (1 (search-forward pattern nil t)) + (-1 (search-backward pattern nil t)) + (2 (let ((pos + (save-excursion + (forward-line + helm-dabbrev-lineno-around) + (point)))) + (setq pos-after pos) + (search-forward pattern pos t))) + (-2 (let ((pos + (save-excursion + (forward-line + (- helm-dabbrev-lineno-around)) + (point)))) + (setq pos-before pos) + (search-backward pattern pos t))))) + (let* ((pbeg (match-beginning 0)) + (replace-regexp (concat "\\(" helm-dabbrev-separator-regexp + "\\)\\'")) + (match-word (helm-dabbrev--search + pattern pbeg replace-regexp))) + (when (and match-word (not (member match-word result))) + (push match-word result))))))) + (catch 'break + (dolist (buf (if all (helm-dabbrev--buffer-list) + (list (current-buffer)))) + (with-current-buffer buf + (when (or minibuf ; check against all buffers when in minibuffer. + (if helm-dabbrev-related-buffer-fn + (funcall helm-dabbrev-related-buffer-fn buffer1) + t)) + (save-excursion + ;; Start searching before thing before point. + (goto-char (- (point) (length str))) + ;; Search the last 30 lines before point. + (funcall search-and-store str -2)) ; store pos [1] + (save-excursion + ;; Search the next 30 lines after point. + (funcall search-and-store str 2)) ; store pos [2] + (save-excursion + ;; Search all before point. + ;; If limit is reached in previous call of + ;; search-and-store pos-before is never set and + ;; goto-char will fail, so check it. + (when pos-before + (goto-char pos-before) ; start from [1] + (funcall search-and-store str -1))) + (save-excursion + ;; Search all after point. + ;; Same comment as above for pos-after. + (when pos-after + (goto-char pos-after) ; start from [2] + (funcall search-and-store str 1))))) + (when (>= (length result) limit) (throw 'break nil)))) + (nreverse result))) + +(defun helm-dabbrev--search (pattern beg sep-regexp) + "Search word or symbol at point matching PATTERN. +Argument BEG is corresponding to the previous match-beginning search. +The search starts at (1- BEG) with a regexp starting with +`helm-dabbrev-separator-regexp' followed by PATTERN followed by a +regexp matching syntactically any word or symbol. +The possible false positives matching SEP-REGEXP at end are finally +removed." + (let ((eol (point-at-eol))) + (save-excursion + (goto-char (1- beg)) + (when (re-search-forward + (concat "\\(" + helm-dabbrev-separator-regexp + "\\)" + "\\(?99:\\(" + (regexp-quote pattern) + "\\(\\sw\\|\\s_\\)+\\)\\)") + eol t) + (replace-regexp-in-string + sep-regexp "" + (match-string-no-properties 99)))))) + +(defun helm-dabbrev--get-candidates (dabbrev &optional limit) + (cl-assert dabbrev nil "[No Match]") + (helm-dabbrev--collect + dabbrev (or limit helm-dabbrev-candidates-number-limit) + (cl-case helm-dabbrev-case-fold-search + (smart (helm-set-case-fold-search-1 dabbrev)) + (t helm-dabbrev-case-fold-search)) + helm-dabbrev-always-search-all)) + +(defun helm-dabbrev-default-action (candidate) + (with-helm-current-buffer + (let* ((limits (helm-bounds-of-thing-before-point + helm-dabbrev-separator-regexp)) + (beg (car limits)) + (end (point))) + (run-with-timer + 0.01 nil + 'helm-insert-completion-at-point + beg end candidate)))) + +;;;###autoload +(cl-defun helm-dabbrev () + "Preconfigured helm for dynamic abbreviations." + (interactive) + (let ((dabbrev (helm-thing-before-point + nil helm-dabbrev-separator-regexp)) + (limits (helm-bounds-of-thing-before-point + helm-dabbrev-separator-regexp)) + (enable-recursive-minibuffers t) + (cycling-disabled-p (or (null helm-dabbrev-cycle-threshold) + (zerop helm-dabbrev-cycle-threshold))) + (helm-execute-action-at-once-if-one t) + (helm-quit-if-no-candidate + (lambda () + (message "[Helm-dabbrev: No expansion found]")))) + (cl-assert (and (stringp dabbrev) (not (string= dabbrev ""))) + nil "[Helm-dabbrev: Nothing found before point]") + (when (and + ;; have been called at least once. + (helm-dabbrev-info-p helm-dabbrev--data) + ;; But user have moved with some other command + ;; in the meaning time. + (not (eq last-command 'helm-dabbrev))) + (setq helm-dabbrev--data nil)) + ;; When candidates are requested in helm directly without cycling, + ;; we need them right now before running helm, so no need to use a + ;; thread here. + (when cycling-disabled-p + (setq helm-dabbrev--cache (helm-dabbrev--get-candidates dabbrev))) + (unless (or cycling-disabled-p + (helm-dabbrev-info-p helm-dabbrev--data)) + (setq helm-dabbrev--data + (make-helm-dabbrev-info + :dabbrev dabbrev + :limits limits + :iterator + (helm-iter-list + (cl-loop for i in (helm-dabbrev--get-candidates + dabbrev helm-dabbrev-cycle-threshold) + when (string-match-p + (concat "^" (regexp-quote dabbrev)) i) + collect i)))) + ;; Thread is released as soon as helm-dabbrev exits after first + ;; insertion so this is unusable for now, keep it like this for + ;; now hooping the situation with threads will be improved in + ;; emacs. The idea is to compute whole list of candidates in + ;; background while cycling with the first + ;; helm-dabbrev-cycle-threshold ones. + (when (and (fboundp 'make-thread) helm-dabbrev-use-thread) + (setq helm-dabbrev--current-thread + (make-thread + (lambda () + (setq helm-dabbrev--cache + (helm-dabbrev--get-candidates dabbrev))))))) + (let ((iter (and (helm-dabbrev-info-p helm-dabbrev--data) + (helm-dabbrev-info-iterator helm-dabbrev--data))) + deactivate-mark) + ;; Cycle until iterator is consumed. + (helm-aif (and iter (helm-iter-next iter)) + (progn + (helm-insert-completion-at-point + (car (helm-dabbrev-info-limits helm-dabbrev--data)) + ;; END is the end of the previous inserted string, not + ;; the end (apart for first insertion) of the initial string. + (cdr limits) it) + ;; Move already tried candidates to end of list. + (push it helm-dabbrev--already-tried)) + ;; Iterator is now empty, reset dabbrev to initial value + ;; and start helm completion. + (let* ((old-dabbrev (if (helm-dabbrev-info-p helm-dabbrev--data) + (helm-dabbrev-info-dabbrev helm-dabbrev--data) + dabbrev)) + (only-one (null (cdr (all-completions + old-dabbrev + helm-dabbrev--already-tried))))) + (unless helm-dabbrev-use-thread + (message "Waiting for helm-dabbrev candidates...") + (setq helm-dabbrev--cache + (helm-dabbrev--get-candidates old-dabbrev))) + ;; If the length of candidates is only one when computed + ;; that's mean the unique matched item have already been + ;; inserted by the iterator, so no need to reinsert the old dabbrev, + ;; just let helm exiting with "No expansion found". + (unless (or only-one cycling-disabled-p) + (setq dabbrev old-dabbrev + limits (helm-dabbrev-info-limits helm-dabbrev--data)) + (setq helm-dabbrev--data nil) + (delete-region (car limits) (point)) + (insert dabbrev)) + ;; Cycling is finished, block until helm-dabbrev--cache have + ;; finished to complete. + (when (and (fboundp 'thread-join) + helm-dabbrev-use-thread + (thread-alive-p helm-dabbrev--current-thread)) + (thread-join helm-dabbrev--current-thread)) + (when (and (null cycling-disabled-p) only-one) + (cl-return-from helm-dabbrev + (message "[Helm-dabbrev: No expansion found]"))) + (with-helm-show-completion (car limits) (cdr limits) + (unwind-protect + (helm :sources + (helm-build-in-buffer-source "Dabbrev Expand" + :data + (cl-loop for cand in helm-dabbrev--cache + unless + (member cand helm-dabbrev--already-tried) + collect cand into lst + finally return + (append lst helm-dabbrev--already-tried)) + :persistent-action 'ignore + :persistent-help "DoNothing" + :keymap helm-dabbrev-map + :action 'helm-dabbrev-default-action + :group 'helm-dabbrev) + :buffer "*helm dabbrev*" + :input (concat "^" dabbrev " ") + :resume 'noresume + :allow-nest t) + (setq helm-dabbrev--already-tried nil)))))))) + +(provide 'helm-dabbrev) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-dabbrev.el ends here diff --git a/elpa/helm-20191031.839/helm-easymenu.el b/elpa/helm-20191031.839/helm-easymenu.el new file mode 100644 index 00000000..eb6878ba --- /dev/null +++ b/elpa/helm-20191031.839/helm-easymenu.el @@ -0,0 +1,87 @@ +;;; helm-easymenu.el --- Helm easymenu definitions. -*- lexical-binding: t -*- + +;; Copyright (C) 2015 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'easymenu) + +(easy-menu-add-item + nil '("Tools") + '("Helm" + ["Find any Files/Buffers" helm-multi-files t] + ["Helm Everywhere (Toggle)" helm-mode t] + ["Helm resume" helm-resume t] + "----" + ("Files" + ["Find files" helm-find-files t] + ["Recent Files" helm-recentf t] + ["Locate" helm-locate t] + ["Search Files with find" helm-find t] + ["Bookmarks" helm-filtered-bookmarks t]) + ("Buffers" + ["Find buffers" helm-buffers-list t]) + ("Commands" + ["Emacs Commands" helm-M-x t] + ["Externals Commands" helm-run-external-command t]) + ("Help" + ["Helm Apropos" helm-apropos t]) + ("Info" + ["Info at point" helm-info-at-point t] + ["Emacs Manual index" helm-info-emacs t] + ["Gnus Manual index" helm-info-gnus t] + ["Helm documentation" helm-documentation t]) + ("Elpa" + ["Elisp packages" helm-list-elisp-packages t] + ["Elisp packages no fetch" helm-list-elisp-packages-no-fetch t]) + ("Tools" + ["Occur" helm-occur t] + ["Grep current directory with AG" helm-do-grep-ag t] + ["Gid" helm-gid t] + ["Etags" helm-etags-select t] + ["Lisp complete at point" helm-lisp-completion-at-point t] + ["Browse Kill ring" helm-show-kill-ring t] + ["Browse register" helm-register t] + ["Mark Ring" helm-all-mark-rings t] + ["Regexp handler" helm-regexp t] + ["Colors & Faces" helm-colors t] + ["Show xfonts" helm-select-xfont t] + ["Ucs Symbols" helm-ucs t] + ["Imenu" helm-imenu t] + ["Imenu all" helm-imenu-in-all-buffers t] + ["Semantic or Imenu" helm-semantic-or-imenu t] + ["Google Suggest" helm-google-suggest t] + ["Eval expression" helm-eval-expression-with-eldoc t] + ["Calcul expression" helm-calcul-expression t] + ["Man pages" helm-man-woman t] + ["Top externals process" helm-top t] + ["Emacs internals process" helm-list-emacs-process t]) + "----" + ["Preferred Options" helm-configuration t]) + "Spell Checking") + +(easy-menu-add-item nil '("Tools") '("----") "Spell Checking") + + +(provide 'helm-easymenu) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-easymenu.el ends here diff --git a/elpa/helm-20191031.839/helm-elisp-package.el b/elpa/helm-20191031.839/helm-elisp-package.el new file mode 100644 index 00000000..77f2c763 --- /dev/null +++ b/elpa/helm-20191031.839/helm-elisp-package.el @@ -0,0 +1,463 @@ +;;; helm-elisp-package.el --- helm interface for package.el -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: +(require 'cl-lib) +(require 'helm) +(require 'helm-help) +(require 'package) + +(defgroup helm-el-package nil + "helm elisp packages." + :group 'helm) + +(defcustom helm-el-package-initial-filter 'all + "Show only installed, upgraded or all packages at startup." + :group 'helm-el-package + :type '(radio :tag "Initial filter for elisp packages" + (const :tag "Show all packages" all) + (const :tag "Show installed packages" installed) + (const :tag "Show not installed packages" uninstalled) + (const :tag "Show upgradable packages" upgrade))) + +(defcustom helm-el-truncate-lines t + "Truncate lines in helm-buffer when non--nil." + :group 'helm-el-package + :type 'boolean) + +;; internals vars +(defvar helm-el-package--show-only 'all) +(defvar helm-el-package--initialized-p nil) +(defvar helm-el-package--tabulated-list nil) +(defvar helm-el-package--upgrades nil) +(defvar helm-el-package--removable-packages nil) + +;; Shutup bytecompiler for emacs-24* +(defvar package-menu-async) ; Only available on emacs-25. +(declare-function async-byte-recompile-directory "ext:async-bytecomp.el") + +(defun helm-el-package--init () + (let (package-menu-async + (inhibit-read-only t)) + (when (null package-alist) + (setq helm-el-package--show-only 'all)) + (when (setq helm-el-package--removable-packages + (package--removable-packages)) + (package-autoremove)) + (unwind-protect + (progn + (save-selected-window + (if helm-el-package--initialized-p + ;; Use this as `list-packages' doesn't work + ;; properly (empty buffer) when called from lisp + ;; with 'no-fetch (emacs-25 WA). + (package-show-package-list) + (when helm--force-updating-p (message "Refreshing packages list...")) + (list-packages helm-el-package--initialized-p)) + (setq helm-el-package--initialized-p t) + (message nil)) + (helm-init-candidates-in-buffer + 'global + (with-current-buffer (get-buffer "*Packages*") + (setq helm-el-package--tabulated-list tabulated-list-entries) + (remove-text-properties (point-min) (point-max) + '(read-only button follow-link category)) + (goto-char (point-min)) + (while (re-search-forward "^[ \t]+" nil t) + (replace-match "")) + (buffer-string))) + (setq helm-el-package--upgrades (helm-el-package-menu--find-upgrades)) + (if helm--force-updating-p + (if helm-el-package--upgrades + (message "Refreshing packages list done, [%d] package(s) to upgrade" + (length helm-el-package--upgrades)) + (message "Refreshing packages list done, no upgrades available")) + (setq helm-el-package--show-only (if helm-el-package--upgrades + 'upgrade + helm-el-package-initial-filter)))) + (kill-buffer "*Packages*")))) + +(defun helm-el-package-describe (candidate) + (let ((id (get-text-property 0 'tabulated-list-id candidate))) + (describe-package (package-desc-name id)))) + +(defun helm-el-package-visit-homepage (candidate) + (let* ((id (get-text-property 0 'tabulated-list-id candidate)) + (pkg (package-desc-name id)) + (desc (cadr (assoc pkg package-archive-contents))) + (extras (package-desc-extras desc)) + (url (and (listp extras) (cdr-safe (assoc :url extras))))) + (if (stringp url) + (browse-url url) + (message "Package %s has no homepage" + (propertize (symbol-name pkg) + 'face 'font-lock-keyword-face))))) + +(defun helm-el-run-visit-homepage () + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-el-package-visit-homepage))) +(put 'helm-el-run-visit-homepage 'helm-only t) + +(defun helm-elisp-package--pkg-name (pkg) + (if (package-desc-p pkg) + (package-desc-name pkg) + pkg)) + +(defun helm-el-package-install-1 (pkg-list) + (cl-loop with mkd = pkg-list + for p in mkd + for id = (get-text-property 0 'tabulated-list-id p) + for name = (helm-elisp-package--pkg-name id) + do (package-install id t) + when (helm-aand (assq name package-alist) + (package-desc-dir (cadr it)) + (file-exists-p it)) + collect id into installed-list and + do (unless (package--user-selected-p name) + (package--save-selected-packages + (cons name package-selected-packages))) + finally do (message (format "%d packages installed:\n(%s)" + (length installed-list) + (mapconcat #'package-desc-full-name + installed-list ", "))))) + +(defun helm-el-package-install (_candidate) + (helm-el-package-install-1 (helm-marked-candidates))) + +(defun helm-el-run-package-install () + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-el-package-install))) +(put 'helm-el-run-package-install 'helm-only t) + +(defun helm-el-package-uninstall-1 (pkg-list &optional force) + (cl-loop with mkd = pkg-list + for p in mkd + for id = (get-text-property 0 'tabulated-list-id p) + do + (condition-case-unless-debug err + (package-delete id force) + (error (message (cadr err)))) + ;; Seems like package-descs are symbols with props instead of + ;; vectors in emacs-27, use package-desc-name to ensure + ;; compatibility in all emacs versions. + unless (assoc (package-desc-name id) package-alist) + collect id into delete-list + finally do (if delete-list + (message (format "%d packages deleted:\n(%s)" + (length delete-list) + (mapconcat #'package-desc-full-name + delete-list ", "))) + "No package deleted"))) + +(defun helm-el-package-uninstall (_candidate) + (helm-el-package-uninstall-1 (helm-marked-candidates) helm-current-prefix-arg)) + +(defun helm-el-run-package-uninstall () + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-el-package-uninstall))) +(put 'helm-el-run-package-uninstall 'helm-only t) + +(defun helm-el-package-menu--find-upgrades () + (cl-loop for entry in helm-el-package--tabulated-list + for pkg-desc = (car entry) + for status = (package-desc-status pkg-desc) + ;; A dependency. + when (string= status "dependency") + collect pkg-desc into dependencies + ;; An installed package used as dependency (user have + ;; installed this package explicitely). + when (package--used-elsewhere-p pkg-desc) + collect pkg-desc into installed-as-dep + ;; An installed package. + when (member status '("installed" "unsigned")) + collect pkg-desc into installed + when (member status '("available" "new")) + collect (cons (package-desc-name pkg-desc) pkg-desc) into available + finally return + ;; Always try to upgrade dependencies before installed. + (cl-loop with all = (append dependencies installed-as-dep installed) + for pkg in all + for name = (package-desc-name pkg) + for avail-pkg = (assq name available) + when (and avail-pkg + (version-list-< + (package-desc-version pkg) + (package-desc-version (cdr avail-pkg)))) + collect avail-pkg))) + +(defun helm-el-package--user-installed-p (package) + "Return non-nil if PACKAGE is a user-installed package." + (let* ((assoc (assq package package-alist)) + (pkg-desc (and assoc (cadr assoc))) + (dir (and pkg-desc (package-desc-dir pkg-desc)))) + (when dir + (file-in-directory-p dir package-user-dir)))) + +(defun helm-el-package-upgrade-1 (pkg-list) + (cl-loop for p in pkg-list + for pkg-desc = (car p) + for pkg-name = (package-desc-name pkg-desc) + for upgrade = (cdr (assq pkg-name + helm-el-package--upgrades)) + do + (cond (;; Install. + (equal pkg-desc upgrade) + (message "Installing package `%s'" pkg-name) + (package-install pkg-desc t)) + (;; Do nothing. + (or (null upgrade) + ;; This may happen when a Elpa version of pkg + ;; is installed and need upgrade and pkg is as + ;; well a builtin package. + (package-built-in-p pkg-name)) + (ignore)) + (;; Delete. + t + (message "Deleting package `%s'" pkg-name) + (package-delete pkg-desc t t))))) + +(defun helm-el-package-upgrade (_candidate) + (helm-el-package-upgrade-1 + (cl-loop with pkgs = (helm-marked-candidates) + for p in helm-el-package--tabulated-list + for pkg = (car p) + if (member (symbol-name (package-desc-name pkg)) pkgs) + collect p))) + +(defun helm-el-run-package-upgrade () + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-el-package-upgrade))) +(put 'helm-el-run-package-upgrade 'helm-only t) + +(defun helm-el-package-upgrade-all () + (if helm-el-package--upgrades + (with-helm-display-marked-candidates + helm-marked-buffer-name (mapcar (lambda (x) (symbol-name (car x))) + helm-el-package--upgrades) + (when (y-or-n-p "Upgrade all packages? ") + (helm-el-package-upgrade-1 helm-el-package--tabulated-list))) + (message "No packages to upgrade actually!"))) + +(defun helm-el-package-upgrade-all-action (_candidate) + (helm-el-package-upgrade-all)) + +(defun helm-el-run-package-upgrade-all () + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-el-package-upgrade-all-action))) +(put 'helm-el-run-package-upgrade-all 'helm-only t) + +(defun helm-el-package--transformer (candidates _source) + (cl-loop for c in candidates + for disp = (concat " " c) + for id = (get-text-property 0 'tabulated-list-id c) + for name = (and id (package-desc-name id)) + for desc = (package-desc-status id) + for built-in-p = (and (package-built-in-p name) + (not (member desc '("available" "new" + "installed" "dependency")))) + for installed-p = (member desc '("installed" "dependency")) + for upgrade-p = (assq name helm-el-package--upgrades) + for user-installed-p = (memq name package-selected-packages) + do (when (and user-installed-p (not upgrade-p)) + (put-text-property 0 2 'display "S " disp)) + do (when (or (memq name helm-el-package--removable-packages) + (and upgrade-p installed-p)) + (put-text-property 0 2 'display "U " disp) + (put-text-property + 2 (+ (length (symbol-name name)) 2) + 'face 'font-lock-variable-name-face disp)) + do (when (and upgrade-p (not installed-p) (not built-in-p)) + (put-text-property 0 2 'display "I " disp)) + for cand = (cons disp (car (split-string disp))) + when (or (and built-in-p + (eq helm-el-package--show-only 'built-in)) + (and upgrade-p + (eq helm-el-package--show-only 'upgrade)) + (and installed-p + (eq helm-el-package--show-only 'installed)) + (and (not installed-p) + (not built-in-p) + (eq helm-el-package--show-only 'uninstalled)) + (eq helm-el-package--show-only 'all)) + collect cand)) + +(defun helm-el-package-show-built-in () + (interactive) + (with-helm-alive-p + (setq helm-el-package--show-only 'built-in) + (helm-update))) +(put 'helm-el-package-show-built-in 'helm-only t) + +(defun helm-el-package-show-upgrade () + (interactive) + (with-helm-alive-p + (setq helm-el-package--show-only 'upgrade) + (helm-update))) +(put 'helm-el-package-show-upgrade 'helm-only t) + +(defun helm-el-package-show-installed () + (interactive) + (with-helm-alive-p + (setq helm-el-package--show-only 'installed) + (helm-update))) +(put 'helm-el-package-show-installed 'helm-only t) + +(defun helm-el-package-show-all () + (interactive) + (with-helm-alive-p + (setq helm-el-package--show-only 'all) + (helm-update))) +(put 'helm-el-package-show-all 'helm-only t) + +(defun helm-el-package-show-uninstalled () + (interactive) + (with-helm-alive-p + (setq helm-el-package--show-only 'uninstalled) + (helm-update))) +(put 'helm-el-package-show-uninstalled 'helm-only t) + +(defvar helm-el-package-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "M-I") 'helm-el-package-show-installed) + (define-key map (kbd "M-O") 'helm-el-package-show-uninstalled) + (define-key map (kbd "M-U") 'helm-el-package-show-upgrade) + (define-key map (kbd "M-B") 'helm-el-package-show-built-in) + (define-key map (kbd "M-A") 'helm-el-package-show-all) + (define-key map (kbd "C-c i") 'helm-el-run-package-install) + (define-key map (kbd "C-c r") 'helm-el-run-package-reinstall) + (define-key map (kbd "C-c d") 'helm-el-run-package-uninstall) + (define-key map (kbd "C-c u") 'helm-el-run-package-upgrade) + (define-key map (kbd "C-c U") 'helm-el-run-package-upgrade-all) + (define-key map (kbd "C-c @") 'helm-el-run-visit-homepage) + map)) + +(defvar helm-source-list-el-package nil) +(defclass helm-list-el-package-source (helm-source-in-buffer) + ((init :initform 'helm-el-package--init) + (get-line :initform 'buffer-substring) + (filtered-candidate-transformer :initform 'helm-el-package--transformer) + (action-transformer :initform 'helm-el-package--action-transformer) + (help-message :initform 'helm-el-package-help-message) + (keymap :initform helm-el-package-map) + (update :initform 'helm-el-package--update) + (candidate-number-limit :initform 9999) + (action :initform '(("Describe package" . helm-el-package-describe) + ("Visit homepage" . helm-el-package-visit-homepage))) + (group :initform 'helm-el-package))) + +(defun helm-el-package--action-transformer (actions candidate) + (let* ((pkg-desc (get-text-property 0 'tabulated-list-id candidate)) + (status (package-desc-status pkg-desc)) + (pkg-name (package-desc-name pkg-desc)) + (built-in (and (package-built-in-p pkg-name) + (not (member status '("available" "new" + "installed" "dependency"))))) + (acts (if helm-el-package--upgrades + (append actions '(("Upgrade all packages" + . helm-el-package-upgrade-all-action))) + actions))) + (cond (built-in '(("Describe package" . helm-el-package-describe))) + ((and (package-installed-p pkg-name) + (cdr (assq pkg-name helm-el-package--upgrades)) + (member status '("installed" "dependency"))) + (append '(("Upgrade package(s)" . helm-el-package-upgrade) + ("Uninstall package(s)" . helm-el-package-uninstall)) + acts)) + ((and (package-installed-p pkg-name) + (cdr (assq pkg-name helm-el-package--upgrades)) + (string= status "available")) + (append '(("Upgrade package(s)" . helm-el-package-upgrade)) + acts)) + ((and (package-installed-p pkg-name) + (or (null (package-built-in-p pkg-name)) + (and (package-built-in-p pkg-name) + (assq pkg-name package-alist)))) + (append acts '(("Reinstall package(s)" . helm-el-package-reinstall) + ("Recompile package(s)" . helm-el-package-recompile) + ("Uninstall package(s)" . helm-el-package-uninstall)))) + (t (append acts '(("Install packages(s)" . helm-el-package-install))))))) + +(defun helm-el-package--update () + (setq helm-el-package--initialized-p nil)) + +(defun helm-el-package-recompile (_pkg) + (cl-loop for p in (helm-marked-candidates) + do (helm-el-package-recompile-1 p))) + +(defun helm-el-package-recompile-1 (pkg) + (let* ((pkg-desc (get-text-property 0 'tabulated-list-id pkg)) + (dir (package-desc-dir pkg-desc))) + (async-byte-recompile-directory dir))) + +(defun helm-el-package-reinstall (_pkg) + (cl-loop for p in (helm-marked-candidates) + for pkg-desc = (get-text-property 0 'tabulated-list-id p) + do (helm-el-package-reinstall-1 pkg-desc))) + +(defun helm-el-package-reinstall-1 (pkg-desc) + (let ((name (package-desc-name pkg-desc))) + (package-delete pkg-desc 'force 'nosave) + ;; pkg-desc contain the description + ;; of the installed package just removed + ;; and is BTW no more valid. + ;; Use the entry in package-archive-content + ;; which is the non--installed package entry. + ;; For some reason `package-install' + ;; need a pkg-desc (package-desc-p) for the build-in + ;; packages already installed, the name (as symbol) + ;; fails with such packages. + (package-install + (cadr (assq name package-archive-contents)) t))) + +(defun helm-el-run-package-reinstall () + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-el-package-reinstall))) +(put 'helm-el-run-package-reinstall 'helm-only t) + +;;;###autoload +(defun helm-list-elisp-packages (arg) + "Preconfigured helm for listing and handling emacs packages." + (interactive "P") + (when arg (setq helm-el-package--initialized-p nil)) + (unless helm-source-list-el-package + (setq helm-source-list-el-package + (helm-make-source "list packages" 'helm-list-el-package-source))) + (helm :sources 'helm-source-list-el-package + :truncate-lines helm-el-truncate-lines + :full-frame t + :buffer "*helm list packages*")) + +;;;###autoload +(defun helm-list-elisp-packages-no-fetch (arg) + "Preconfigured helm for emacs packages. + +Same as `helm-list-elisp-packages' but don't fetch packages on remote. +Called with a prefix ARG always fetch packages on remote." + (interactive "P") + (let ((helm-el-package--initialized-p (null arg))) + (helm-list-elisp-packages nil))) + +(provide 'helm-elisp-package) + +;;; helm-elisp-package.el ends here diff --git a/elpa/helm-20191031.839/helm-elisp.el b/elpa/helm-20191031.839/helm-elisp.el new file mode 100644 index 00000000..78a5a3ce --- /dev/null +++ b/elpa/helm-20191031.839/helm-elisp.el @@ -0,0 +1,984 @@ +;;; helm-elisp.el --- Elisp symbols completion for helm. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: +(require 'cl-lib) +(require 'helm) +(require 'helm-lib) +(require 'helm-help) +(require 'helm-types) +(require 'helm-utils) +(require 'helm-info) +(require 'helm-eval) +(require 'helm-files) + +(declare-function 'helm-describe-function "helm-lib") +(declare-function 'helm-describe-variable "helm-lib") +(declare-function 'helm-describe-face "helm-lib") + + +;;; Customizable values + +(defgroup helm-elisp nil + "Elisp related Applications and libraries for Helm." + :group 'helm) + +(defcustom helm-turn-on-show-completion t + "Display candidate in `current-buffer' while moving selection when non--nil." + :group 'helm-elisp + :type 'boolean) + +(defcustom helm-show-completion-min-window-height 7 + "Minimum completion window height used in show completion. +This is used in macro `with-helm-show-completion'." + :group 'helm-elisp + :type 'integer) + +(defcustom helm-lisp-quoted-function-list + '(funcall apply mapc cl-mapc mapcar cl-mapcar + callf callf2 cl-callf cl-callf2 fset + fboundp fmakunbound symbol-function) + "List of function where quoted function completion happen. +e.g give only function names after \(funcall '." + :group 'helm-elisp + :type '(repeat (choice symbol))) + +(defcustom helm-lisp-unquoted-function-list + '(function defadvice) + "List of function where unquoted function completion happen. +e.g give only function names after \(function ." + :group 'helm-elisp + :type '(repeat (choice symbol))) + +(defcustom helm-apropos-fuzzy-match nil + "Enable fuzzy matching for `helm-apropos' when non-nil." + :group 'helm-elisp + :type 'boolean) + +(defcustom helm-lisp-fuzzy-completion nil + "Enable fuzzy matching in emacs-lisp completion when non-nil. +NOTE: This enable fuzzy matching in helm native implementation of +elisp completion, but not on helmized elisp completion, i.e +fuzzy completion is not available in `completion-at-point'." + :group 'helm-elisp + :type 'boolean) + +(defcustom helm-apropos-function-list '(helm-def-source--emacs-commands + helm-def-source--emacs-functions + helm-def-source--eieio-classes + helm-def-source--eieio-generic + helm-def-source--emacs-variables + helm-def-source--emacs-faces) + "A list of functions that build helm sources to use in `helm-apropos'." + :group 'helm-elisp + :type '(repeat (choice symbol))) + +(defcustom helm-apropos-defaut-info-lookup-sources '(helm-source-info-elisp + helm-source-info-cl + helm-source-info-eieio) + "A list of sources to look into when searching info page of a symbol." + :group 'helm-elisp + :type '(repeat (choice symbol))) + +(defcustom helm-show-completion-display-function + (if (display-graphic-p) + #'helm-display-buffer-in-own-frame + #'helm-show-completion-default-display-function) + "The function used to display helm completion buffer. + +This function is used by `with-helm-show-completion', when nil +fallback to `helm-default-display-buffer'. + +Default is to use a separate frame on graphic display and +`helm-show-completion-default-display-function' on non graphic +display." + :group 'helm-elisp + :type 'function) + +;;; Faces +;; +;; +(defgroup helm-elisp-faces nil + "Customize the appearance of helm-elisp." + :prefix "helm-" + :group 'helm-elisp + :group 'helm-faces) + +(defface helm-lisp-show-completion + '((t (:background "DarkSlateGray"))) + "Face used for showing candidates in `helm-lisp-completion'." + :group 'helm-elisp-faces) + +(defface helm-lisp-completion-info + '((t (:foreground "red"))) + "Face used for showing info in `helm-lisp-completion'." + :group 'helm-elisp-faces) + +(defcustom helm-elisp-help-function + 'helm-elisp-show-help + "Function for displaying help for Lisp symbols." + :group 'helm-elisp + :type '(choice (function :tag "Open help for the symbol." + helm-elisp-show-help) + (function :tag "Show one liner in modeline." + helm-elisp-show-doc-modeline))) + +(defcustom helm-locate-library-fuzzy-match t + "Enable fuzzy-matching in `helm-locate-library' when non--nil." + :type 'boolean + :group 'helm-elisp) + + +;;; Show completion. +;; +;; Provide show completion with macro `with-helm-show-completion'. + +(defvar helm-show-completion-overlay nil) + +;; Called each time cursor move in helm-buffer. +(defun helm-show-completion () + (with-helm-current-buffer + (overlay-put helm-show-completion-overlay + 'display (substring-no-properties + (helm-get-selection))))) + +(defun helm-show-completion-init-overlay (beg end) + (setq helm-show-completion-overlay (make-overlay beg end)) + (overlay-put helm-show-completion-overlay + 'face 'helm-lisp-show-completion)) + +(defun helm-show-completion-default-display-function (buffer &rest _args) + "A special resized helm window is used depending on position in BUFFER." + (with-selected-window (selected-window) + (if (window-dedicated-p) + (helm-default-display-buffer buffer) + (let* ((screen-size (+ (count-screen-lines (window-start) (point) t) + 1 ; mode-line + (if header-line-format 1 0))) ; header-line + (def-size (- (window-height) + helm-show-completion-min-window-height)) + (upper-height (max window-min-height (min screen-size def-size))) + split-window-keep-point) + (recenter -1) + (set-window-buffer (if (active-minibuffer-window) + (minibuffer-selected-window) + (split-window nil upper-height + helm-split-window-default-side)) + buffer))))) + +(defmacro with-helm-show-completion (beg end &rest body) + "Show helm candidate in an overlay at point. +BEG and END are the beginning and end position of the current completion +in `helm-current-buffer'. +BODY is an helm call where we want to enable show completion. +If `helm-turn-on-show-completion' is nil do nothing." + (declare (indent 2) (debug t)) + `(unwind-protect + (if helm-turn-on-show-completion + (let ((helm-move-selection-after-hook + (append (list 'helm-show-completion) + helm-move-selection-after-hook)) + (helm-split-window-default-side + (if (eq helm-split-window-default-side 'same) + 'below helm-split-window-default-side)) + helm-split-window-inside-p + helm-reuse-last-window-split-state) + (helm-set-local-variable + 'helm-display-function + (or helm-show-completion-display-function + 'helm-default-display-buffer)) + (helm-show-completion-init-overlay ,beg ,end) + ,@body) + ,@body) + (when (and helm-show-completion-overlay + (overlayp helm-show-completion-overlay)) + (delete-overlay helm-show-completion-overlay)))) + + +;;; Lisp symbol completion. +;; +;; +(defun helm-lisp-completion--predicate-at-point (beg) + ;; Return a predicate for `all-completions'. + (let ((fn-sym-p (lambda () + (or + (and (eq (char-before) ?\ ) + (save-excursion + (skip-syntax-backward " " (point-at-bol)) + (memq (symbol-at-point) + helm-lisp-unquoted-function-list))) + (and (eq (char-before) ?\') + (save-excursion + (forward-char -1) + (eq (char-before) ?\#))))))) + (save-excursion + (goto-char beg) + (if (or + ;; Complete on all symbols in non--lisp modes (logs mail etc..) + (not (memq major-mode '(emacs-lisp-mode + lisp-interaction-mode + inferior-emacs-lisp-mode))) + (not (or (funcall fn-sym-p) + (and (eq (char-before) ?\') + (save-excursion + (forward-char (if (funcall fn-sym-p) -2 -1)) + (skip-syntax-backward " " (point-at-bol)) + (memq (symbol-at-point) + helm-lisp-quoted-function-list))) + (eq (char-before) ?\())) ; no paren before str. + ;; Looks like we are in a let statement. + (condition-case nil + (progn (up-list -2) (forward-char 1) + (eq (char-after) ?\()) + (error nil))) + (lambda (sym) + (or (boundp sym) (fboundp sym) (symbol-plist sym))) + #'fboundp)))) + +(defun helm-thing-before-point (&optional limits regexp) + "Return symbol name before point. +If REGEXP is specified return what REGEXP find before point. +By default match the beginning of symbol before point. +With LIMITS arg specified return the beginning and end position +of symbol before point." + (save-excursion + (let (beg + (end (point)) + (boundary (field-beginning nil nil (point-at-bol)))) + (if (re-search-backward (or regexp "\\_<") boundary t) + (setq beg (match-end 0)) + (setq beg boundary)) + (unless (= beg end) + (if limits + (cons beg end) + (buffer-substring-no-properties beg end)))))) + +(defun helm-bounds-of-thing-before-point (&optional regexp) + "Get the beginning and end position of `helm-thing-before-point'. +Return a cons \(beg . end\)." + (helm-thing-before-point 'limits regexp)) + +(defun helm-insert-completion-at-point (beg end str) + ;; When there is no space after point + ;; we are completing inside a symbol or + ;; after a partial symbol with the next arg aside + ;; without space, in this case mark the region. + ;; deleting it would remove the + ;; next arg which is unwanted. + (delete-region beg end) + (insert str) + (let ((pos (cdr (or (bounds-of-thing-at-point 'symbol) + ;; needed for helm-dabbrev. + (bounds-of-thing-at-point 'filename))))) + (when (and pos (< (point) pos)) + (push-mark pos t t)))) + +(defvar helm-lisp-completion--cache nil) +(defvar helm-lgst-len nil) +;;;###autoload +(defun helm-lisp-completion-at-point () + "Preconfigured helm for lisp symbol completion at point." + (interactive) + (setq helm-lgst-len 0) + (let* ((target (helm-thing-before-point)) + (beg (car (helm-bounds-of-thing-before-point))) + (end (point)) + (pred (and beg (helm-lisp-completion--predicate-at-point beg))) + (loc-vars (and (fboundp 'elisp--local-variables) + (ignore-errors + (mapcar #'symbol-name (elisp--local-variables))))) + (glob-syms (and target pred (all-completions target obarray pred))) + (candidates (append loc-vars glob-syms)) + (helm-quit-if-no-candidate t) + (helm-execute-action-at-once-if-one t) + (enable-recursive-minibuffers t)) + (setq helm-lisp-completion--cache (cl-loop for sym in candidates + for len = (length sym) + when (> len helm-lgst-len) + do (setq helm-lgst-len len) + collect sym)) + (if candidates + (with-helm-show-completion beg end + ;; Overlay is initialized now in helm-current-buffer. + (helm + :sources (helm-build-in-buffer-source "Lisp completion" + :data helm-lisp-completion--cache + :persistent-action `(helm-lisp-completion-persistent-action . + ,(and (eq helm-elisp-help-function + 'helm-elisp-show-doc-modeline) + 'never-split)) + :nomark t + :match-part (lambda (c) (car (split-string c))) + :fuzzy-match helm-lisp-fuzzy-completion + :persistent-help (helm-lisp-completion-persistent-help) + :filtered-candidate-transformer + 'helm-lisp-completion-transformer + :action (lambda (candidate) + (with-helm-current-buffer + (run-with-timer + 0.01 nil + 'helm-insert-completion-at-point + beg end candidate)))) + :input (if helm-lisp-fuzzy-completion + target (concat target " ")) + :resume 'noresume + :truncate-lines t + :buffer "*helm lisp completion*" + :allow-nest t)) + (message "[No Match]")))) + +(defun helm-lisp-completion-persistent-action (candidate &optional name) + "Show documentation for the function. +Documentation is shown briefly in mode-line or completely +in other window according to the value of `helm-elisp-help-function'." + (funcall helm-elisp-help-function candidate name)) + +(defun helm-lisp-completion-persistent-help () + "Return persistent-help according to the value of `helm-elisp-help-function'" + (cl-ecase helm-elisp-help-function + (helm-elisp-show-doc-modeline "Show brief doc in mode-line") + (helm-elisp-show-help "Toggle show help for the symbol"))) + +(defun helm-elisp--show-help-1 (candidate &optional name) + (let ((sym (intern-soft candidate))) + (cl-typecase sym + ((and fboundp boundp) + (if (member name `(,helm-describe-function-function ,helm-describe-variable-function)) + (funcall (intern (format "helm-%s" name)) sym) + ;; When there is no way to know what to describe + ;; prefer describe-function. + (helm-describe-function sym))) + (fbound (helm-describe-function sym)) + (bound (helm-describe-variable sym)) + (face (helm-describe-face sym))))) + +(defun helm-elisp-show-help (candidate &optional name) + "Show full help for the function CANDIDATE. +Arg NAME specify the name of the top level function +calling helm generic completion (e.g \"describe-function\") +which allow calling the right function when CANDIDATE symbol +refers at the same time to variable and a function." + (helm-elisp--persistent-help + candidate 'helm-elisp--show-help-1 name)) + +(defun helm-elisp-show-doc-modeline (candidate &optional name) + "Show brief documentation for the function in modeline." + (let ((cursor-in-echo-area t) + mode-line-in-non-selected-windows) + (helm-show-info-in-mode-line + (propertize + (helm-get-first-line-documentation + (intern candidate) name) + 'face 'helm-lisp-completion-info)))) + +(defun helm-lisp-completion-transformer (candidates _source) + "Helm candidates transformer for lisp completion." + (cl-loop for c in candidates + for sym = (intern c) + for annot = (cl-typecase sym + (command " (Com)") + (class " (Class)") + (generic " (Gen)") + (fbound " (Fun)") + (bound " (Var)") + (face " (Face)")) + for spaces = (make-string (- helm-lgst-len (length c)) ? ) + collect (cons (concat c spaces annot) c) into lst + finally return (sort lst #'helm-generic-sort-fn))) + +(defun helm-get-first-line-documentation (sym &optional name) + "Return first line documentation of symbol SYM. +If SYM is not documented, return \"Not documented\"." + (let ((doc (cl-typecase sym + ((and fboundp boundp) + (cond ((string= name "describe-function") + (documentation sym t)) + ((string= name "describe-variable") + (documentation-property sym 'variable-documentation t)) + (t (documentation sym t)))) + (fbound (documentation sym t)) + (bound (documentation-property sym 'variable-documentation t)) + (face (face-documentation sym))))) + (if (and doc (not (string= doc "")) + ;; `documentation' return "\n\n(args...)" + ;; for CL-style functions. + (not (string-match-p "^\n\n" doc))) + (car (split-string doc "\n")) + "Not documented"))) + +;;; File completion. +;; +;; Complete file name at point. + +;;;###autoload +(defun helm-complete-file-name-at-point (&optional force) + "Preconfigured helm to complete file name at point." + (interactive) + (require 'helm-mode) + (let* ((tap (thing-at-point 'filename)) + beg + (init (and tap + (or force + (save-excursion + (end-of-line) + (search-backward tap (point-at-bol) t) + (setq beg (point)) + (looking-back "[^'`( ]" (1- (point))))) + (expand-file-name + (substring-no-properties tap)))) + (end (point)) + (helm-quit-if-no-candidate t) + (helm-execute-action-at-once-if-one t) + completion) + (with-helm-show-completion beg end + (setq completion (helm-read-file-name "FileName: " + :initial-input init))) + (when (and completion (not (string= completion ""))) + (delete-region beg end) (insert (if (string-match "^~" tap) + (abbreviate-file-name completion) + completion))))) + +;;;###autoload +(defun helm-lisp-indent () + ;; It is meant to use with `helm-define-multi-key' which + ;; does not support args for functions yet, so use `current-prefix-arg' + ;; for now instead of (interactive "P"). + (interactive) + (let ((tab-always-indent (or (eq tab-always-indent 'complete) + tab-always-indent))) + (indent-for-tab-command current-prefix-arg))) + +;;;###autoload +(defun helm-lisp-completion-or-file-name-at-point () + "Preconfigured helm to complete lisp symbol or filename at point. +Filename completion happen if string start after or between a double quote." + (interactive) + (let* ((tap (thing-at-point 'filename))) + (if (and tap (save-excursion + (end-of-line) + (search-backward tap (point-at-bol) t) + (looking-back "[^'`( ]" (1- (point))))) + (helm-complete-file-name-at-point) + (helm-lisp-completion-at-point)))) + + +;;; Apropos +;; +;; +(defvar helm-apropos-history nil) + +(defun helm-apropos-init (test default) + "Init candidates buffer for `helm-apropos' sources." + (require 'helm-help) + (helm-init-candidates-in-buffer 'global + (let ((default-symbol (and (stringp default) + (intern-soft default))) + (symbols (all-completions "" obarray test))) + (if (and default-symbol (funcall test default-symbol)) + (cons default-symbol symbols) + symbols)))) + +(defun helm-apropos-init-faces (default) + "Init candidates buffer for faces for `helm-apropos'." + (require 'helm-help) + (with-current-buffer (helm-candidate-buffer 'global) + (goto-char (point-min)) + (let ((default-symbol (and (stringp default) + (intern-soft default))) + (faces (face-list))) + (when (and default-symbol (facep default-symbol)) + (insert (concat default "\n"))) + (insert + (mapconcat #'prin1-to-string + (if default + (cl-remove-if (lambda (sym) (string= sym default)) faces) + faces) + "\n"))))) + +(defun helm-apropos-default-sort-fn (candidates _source) + (if (string= helm-pattern "") + candidates + (sort candidates #'helm-generic-sort-fn))) + +(defun helm-apropos-clean-history-variable (candidate) + (with-helm-current-buffer ; var is maybe local + (let* ((sym (intern-soft candidate)) + (cands (symbol-value sym)) + (mkds (and (listp cands) + (helm-comp-read "Delete entry: " + cands :marked-candidates t)))) + (cl-assert (listp mkds) nil "Variable value is not a list") + (cl-loop for elm in mkds do + (if (local-variable-p sym) + (set (make-local-variable sym) + (setq cands (delete elm cands))) + (set sym (setq cands (delete elm cands)))))))) + +(defun helm-apropos-clean-ring (candidate) + (with-helm-current-buffer ; var is maybe local + (let* ((sym (intern-soft candidate)) + (val (symbol-value sym)) + (cands (and (ring-p val) (ring-elements val))) + (mkds (and cands (helm-comp-read + "Delete entry: " + cands :marked-candidates t)))) + (when mkds + (cl-loop for elm in mkds do + (ring-remove + val (helm-position + elm + (ring-elements val) + :test 'equal)) + and do (if (local-variable-p sym) + (set (make-local-variable sym) val) + (set sym val))))))) + +(defun helm-apropos-action-transformer (actions candidate) + (let* ((sym (helm-symbolify candidate)) + (val (with-helm-current-buffer (symbol-value sym)))) + (cond ((custom-variable-p sym) + (append + actions + (let ((standard-value (eval (car (get sym 'standard-value))))) + (unless (equal standard-value (symbol-value sym)) + `(("Reset Variable to default value" + . ,(lambda (candidate) + (let ((sym (helm-symbolify candidate))) + (set sym standard-value))))))) + '(("Customize variable" . + (lambda (candidate) + (customize-option (helm-symbolify candidate))))))) + ((and val (with-helm-current-buffer (ring-p (symbol-value sym)))) + (append actions + '(("Clean ring" . helm-apropos-clean-ring)))) + ((and (string-match-p "history" candidate) (listp val)) + (append actions + '(("Clean variable" . + helm-apropos-clean-history-variable)))) + (t actions)))) + +(defun helm-def-source--emacs-variables (&optional default) + (helm-build-in-buffer-source "Variables" + :init (lambda () + (helm-apropos-init + (lambda (x) (and (boundp x) (not (keywordp x)))) default)) + :fuzzy-match helm-apropos-fuzzy-match + :filtered-candidate-transformer (and (null helm-apropos-fuzzy-match) + 'helm-apropos-default-sort-fn) + :nomark t + :persistent-action (lambda (candidate) + (helm-elisp--persistent-help + candidate 'helm-describe-variable)) + :persistent-help "Toggle describe variable" + :action '(("Describe variable" . helm-describe-variable) + ("Find variable" . helm-find-variable) + ("Info lookup" . helm-info-lookup-symbol) + ("Set variable" . helm-set-variable)) + :action-transformer 'helm-apropos-action-transformer)) + +(defun helm-def-source--emacs-faces (&optional default) + "Create `helm' source for faces to be displayed with +`helm-apropos'." + (helm-build-in-buffer-source "Faces" + :init (lambda () (helm-apropos-init-faces default)) + :fuzzy-match helm-apropos-fuzzy-match + :filtered-candidate-transformer + (append (and (null helm-apropos-fuzzy-match) + '(helm-apropos-default-sort-fn)) + (list + (lambda (candidates _source) + (cl-loop for c in candidates + collect (propertize c 'face (intern c)))))) + :persistent-action (lambda (candidate) + (helm-elisp--persistent-help + candidate 'helm-describe-face)) + :persistent-help "Toggle describe face" + :action '(("Describe face" . helm-describe-face) + ("Find face" . helm-find-face-definition) + ("Customize face" . (lambda (candidate) + (customize-face (helm-symbolify candidate))))))) + +(defun helm-def-source--emacs-commands (&optional default) + (helm-build-in-buffer-source "Commands" + :init (lambda () + (helm-apropos-init 'commandp default)) + :fuzzy-match helm-apropos-fuzzy-match + :filtered-candidate-transformer (and (null helm-apropos-fuzzy-match) + 'helm-apropos-default-sort-fn) + :nomark t + :persistent-action (lambda (candidate) + (helm-elisp--persistent-help + candidate 'helm-describe-function)) + :persistent-help "Toggle describe command" + :action '(("Describe function" . helm-describe-function) + ("Find function" . helm-find-function) + ("Info lookup" . helm-info-lookup-symbol)))) + +(defun helm-def-source--emacs-functions (&optional default) + (helm-build-in-buffer-source "Functions" + :init (lambda () + (helm-apropos-init (lambda (x) + (and (fboundp x) + (not (commandp x)) + (not (generic-p x)) + (not (class-p x)))) + default)) + :fuzzy-match helm-apropos-fuzzy-match + :filtered-candidate-transformer (and (null helm-apropos-fuzzy-match) + 'helm-apropos-default-sort-fn) + :persistent-action (lambda (candidate) + (helm-elisp--persistent-help + candidate 'helm-describe-function)) + :persistent-help "Toggle describe function" + :nomark t + :action '(("Describe function" . helm-describe-function) + ("Find function" . helm-find-function) + ("Info lookup" . helm-info-lookup-symbol)))) + +(defun helm-def-source--eieio-classes (&optional default) + (helm-build-in-buffer-source "Classes" + :init (lambda () + (helm-apropos-init (lambda (x) + (class-p x)) + default)) + :fuzzy-match helm-apropos-fuzzy-match + :filtered-candidate-transformer (and (null helm-apropos-fuzzy-match) + 'helm-apropos-default-sort-fn) + :nomark t + :persistent-action (lambda (candidate) + (helm-elisp--persistent-help + candidate 'helm-describe-class)) + :persistent-help "Toggle describe class" + :action '(("Describe Class" . helm-describe-class) + ("Find Class" . helm-find-function) + ("Info lookup" . helm-info-lookup-symbol)))) + +(defun helm-def-source--eieio-generic (&optional default) + (helm-build-in-buffer-source "Generic functions" + :init (lambda () + (helm-apropos-init (lambda (x) + (generic-p x)) + default)) + :fuzzy-match helm-apropos-fuzzy-match + :filtered-candidate-transformer (and (null helm-apropos-fuzzy-match) + 'helm-apropos-default-sort-fn) + :nomark t + :persistent-action (lambda (candidate) + (helm-elisp--persistent-help + candidate 'helm-describe-function)) + :persistent-help "Toggle describe generic function" + :action '(("Describe function" . helm-describe-function) + ("Find function" . helm-find-function) + ("Info lookup" . helm-info-lookup-symbol)))) + +(defun helm-info-lookup-fallback-source (candidate) + (let ((sym (helm-symbolify candidate)) + src-name fn) + (cond ((class-p sym) + (setq fn #'helm-describe-function + src-name "Describe class")) + ((generic-p sym) + (setq fn #'helm-describe-function + src-name "Describe generic function")) + ((fboundp sym) + (setq fn #'helm-describe-function + src-name "Describe function")) + ((facep sym) + (setq fn #'helm-describe-face + src-name "Describe face")) + (t + (setq fn #'helm-describe-variable + src-name "Describe variable"))) + (helm-build-sync-source src-name + :candidates (list candidate) + :persistent-action (lambda (candidate) + (helm-elisp--persistent-help + candidate fn)) + :persistent-help src-name + :nomark t + :action fn))) + +(defun helm-info-lookup-symbol-1 (c) + (let ((helm-execute-action-at-once-if-one 'current-source)) + (helm :sources (append helm-apropos-defaut-info-lookup-sources + (list (helm-info-lookup-fallback-source c))) + :resume 'noresume + :buffer "*helm lookup*" + :input c))) + +(defun helm-info-lookup-symbol (candidate) + ;; ???:Running an idle-timer allows not catching RET when exiting + ;; with the fallback source. + ;; (run-with-idle-timer 0.01 nil #'helm-info-lookup-symbol-1 candidate) + (helm-info-lookup-symbol-1 candidate)) + +;;;###autoload +(defun helm-apropos (default) + "Preconfigured helm to describe commands, functions, variables and faces. +In non interactives calls DEFAULT argument should be provided as a string, +i.e the `symbol-name' of any existing symbol." + (interactive (list (thing-at-point 'symbol))) + (helm :sources + (mapcar (lambda (func) + (funcall func default)) + helm-apropos-function-list) + :history 'helm-apropos-history + :buffer "*helm apropos*" + :preselect (and default (concat "\\_<" (regexp-quote default) "\\_>")))) + + +;;; Advices +;; +;; +(defvar helm-source-advice + (helm-build-sync-source "Function Advice" + :init (lambda () (require 'advice)) + :candidates 'helm-advice-candidates + :action (helm-make-actions "Toggle Enable/Disable" 'helm-advice-toggle) + :persistent-action 'helm-advice-persistent-action + :nomark t + :multiline t + :persistent-help "Toggle describe function / C-u C-j: Toggle advice")) + +(defun helm-advice-candidates () + (cl-loop for (fname) in ad-advised-functions + for function = (intern fname) + append + (cl-loop for class in ad-advice-classes append + (cl-loop for advice in (ad-get-advice-info-field function class) + for enabled = (ad-advice-enabled advice) + collect + (cons (format + "%s %s %s" + (if enabled "Enabled " "Disabled") + (propertize fname 'face 'font-lock-function-name-face) + (ad-make-single-advice-docstring advice class nil)) + (list function class advice)))))) + +(defun helm-advice-persistent-action (func-class-advice) + (if current-prefix-arg + (helm-advice-toggle func-class-advice) + (describe-function (car func-class-advice)))) + +(defun helm-advice-toggle (func-class-advice) + (cl-destructuring-bind (function _class advice) func-class-advice + (cond ((ad-advice-enabled advice) + (ad-advice-set-enabled advice nil) + (message "Disabled")) + (t + (ad-advice-set-enabled advice t) + (message "Enabled"))) + (ad-activate function) + (and helm-in-persistent-action + (helm-advice-update-current-display-string)))) + +(defun helm-advice-update-current-display-string () + (helm-edit-current-selection + (let ((newword (cond ((looking-at "Disabled") "Enabled") + ((looking-at "Enabled") "Disabled")))) + (when newword + (delete-region (point) (progn (forward-word 1) (point))) + (insert newword))))) + +;;;###autoload +(defun helm-manage-advice () + "Preconfigured `helm' to disable/enable function advices." + (interactive) + (helm-other-buffer 'helm-source-advice "*helm advice*")) + + +;;; Locate elisp library +;; +;; +(defun helm-locate-library-scan-list () + (cl-loop for dir in load-path + with load-suffixes = '(".el") + when (file-directory-p dir) + append (directory-files + dir t (concat (regexp-opt (get-load-suffixes)) + "\\'")))) + +;;;###autoload +(defun helm-locate-library () + "Preconfigured helm to locate elisp libraries." + (interactive) + (helm :sources (helm-build-in-buffer-source "Elisp libraries (Scan)" + :data #'helm-locate-library-scan-list + :fuzzy-match helm-locate-library-fuzzy-match + :keymap helm-generic-files-map + :search (unless helm-locate-library-fuzzy-match + (lambda (regexp) + (re-search-forward + (if helm-ff-transformer-show-only-basename + (replace-regexp-in-string + "\\`\\^" "" regexp) + regexp) + nil t))) + :match-part (lambda (candidate) + (with-helm-buffer + (if helm-ff-transformer-show-only-basename + (helm-basename candidate) candidate))) + :filter-one-by-one (lambda (c) + (with-helm-buffer + (if helm-ff-transformer-show-only-basename + (cons (helm-basename c) c) c))) + :action (helm-actions-from-type-file)) + :ff-transformer-show-only-basename nil + :buffer "*helm locate library*")) + +(defun helm-set-variable (var) + "Set VAR value interactively." + (let* ((sym (helm-symbolify var)) + (val (default-value sym))) + (set-default sym (eval-minibuffer + (format "Set `%s': " var) + (if (or (stringp val) + (memq val '(nil t)) + (numberp val)) + (prin1-to-string val) + (format "'%s" (prin1-to-string val))))))) + + +;;; Elisp Timers. +;; +;; +(defclass helm-absolute-time-timers-class (helm-source-sync helm-type-timers) + ((candidates :initform timer-list) + (allow-dups :initform t) + (candidate-transformer + :initform + (lambda (candidates) + (cl-loop for timer in candidates + collect (cons (helm-elisp--format-timer timer) timer)))))) + +(defvar helm-source-absolute-time-timers + (helm-make-source "Absolute Time Timers" 'helm-absolute-time-timers-class)) + +(defclass helm-idle-time-timers-class (helm-source-sync helm-type-timers) + ((candidates :initform timer-idle-list) + (allow-dups :initform t) + (candidate-transformer + :initform + (lambda (candidates) + (cl-loop for timer in candidates + collect (cons (helm-elisp--format-timer timer) timer)))))) + +(defvar helm-source-idle-time-timers + (helm-make-source "Idle Time Timers" 'helm-idle-time-timers-class)) + +(defun helm-elisp--format-timer (timer) + (format "%s repeat=%s %s(%s)" + (let ((time (timer--time timer))) + (if (timer--idle-delay timer) + (format-time-string "idle-for=%5s" time) + (format-time-string "%m/%d %T" time))) + (or (timer--repeat-delay timer) "nil") + (mapconcat 'identity (split-string + (prin1-to-string (timer--function timer)) + "\n") " ") + (mapconcat 'prin1-to-string (timer--args timer) " "))) + +;;;###autoload +(defun helm-timers () + "Preconfigured `helm' for timers." + (interactive) + (helm :sources '(helm-source-absolute-time-timers + helm-source-idle-time-timers) + :buffer "*helm timers*")) + + +;;; Complex command history +;; +;; +(defun helm-btf--usable-p () + "Return t if current version of `backtrace-frame' accept 2 arguments." + (condition-case nil + (progn (backtrace-frame 1 'condition-case) t) + (wrong-number-of-arguments nil))) + +(if (helm-btf--usable-p) ; Check if BTF accept more than one arg. + ;; Emacs 24.4. + (dont-compile + (defvar helm-sexp--last-sexp nil) + ;; This wont work compiled. + (defun helm-sexp-eval-1 () + (interactive) + (unwind-protect + (progn + ;; Trick called-interactively-p into thinking that `cand' is + ;; an interactive call, See `repeat-complex-command'. + (add-hook 'called-interactively-p-functions + #'helm-complex-command-history--called-interactively-skip) + (eval (read helm-sexp--last-sexp))) + (remove-hook 'called-interactively-p-functions + #'helm-complex-command-history--called-interactively-skip))) + + (defun helm-complex-command-history--called-interactively-skip (i _frame1 frame2) + (and (eq 'eval (cadr frame2)) + (eq 'helm-sexp-eval-1 + (cadr (backtrace-frame (+ i 2) #'called-interactively-p))) + 1)) + + (defun helm-sexp-eval (_candidate) + (call-interactively #'helm-sexp-eval-1))) + ;; Emacs 24.3 + (defun helm-sexp-eval (cand) + (let ((sexp (read cand))) + (condition-case err + (if (> (length (remove nil sexp)) 1) + (eval sexp) + (apply 'call-interactively sexp)) + (error (message "Evaluating gave an error: %S" err) + nil))))) + +(defvar helm-source-complex-command-history + (helm-build-sync-source "Complex Command History" + :candidates (lambda () + ;; Use cdr to avoid adding + ;; `helm-complex-command-history' here. + (cl-loop for i in command-history + unless (equal i '(helm-complex-command-history)) + collect (prin1-to-string i))) + :action (helm-make-actions + "Eval" (lambda (candidate) + (and (boundp 'helm-sexp--last-sexp) + (setq helm-sexp--last-sexp candidate)) + (let ((command (read candidate))) + (unless (equal command (car command-history)) + (setq command-history (cons command command-history)))) + (run-with-timer 0.1 nil #'helm-sexp-eval candidate)) + "Edit and eval" (lambda (candidate) + (edit-and-eval-command "Eval: " (read candidate)))) + :persistent-action #'helm-sexp-eval + :multiline t)) + +;;;###autoload +(defun helm-complex-command-history () + "Preconfigured helm for complex command history." + (interactive) + (helm :sources 'helm-source-complex-command-history + :buffer "*helm complex commands*")) + +(provide 'helm-elisp) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-elisp.el ends here diff --git a/elpa/helm-20191031.839/helm-eshell.el b/elpa/helm-20191031.839/helm-eshell.el new file mode 100644 index 00000000..ac7c9003 --- /dev/null +++ b/elpa/helm-20191031.839/helm-eshell.el @@ -0,0 +1,488 @@ +;;; helm-eshell.el --- pcomplete and eshell completion for helm. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Commentary: +;; +;; Enable like this in .emacs: +;; (add-hook 'eshell-mode-hook +;; (lambda () +;; (eshell-cmpl-initialize) +;; (define-key eshell-mode-map [remap eshell-pcomplete] 'helm-esh-pcomplete) +;; (define-key eshell-mode-map (kbd "M-s f") 'helm-eshell-prompts-all))) +;; (define-key eshell-mode-map (kbd "M-r") 'helm-eshell-history))) + + +;;; Code: +(require 'cl-lib) +(require 'helm) +(require 'helm-lib) +(require 'helm-help) +(require 'helm-elisp) + +(declare-function eshell-read-aliases-list "em-alias") +(declare-function eshell-send-input "esh-mode" (&optional use-region queue-p no-newline)) +(declare-function eshell-bol "esh-mode") +(declare-function eshell-parse-arguments "esh-arg" (beg end)) +(declare-function eshell-backward-argument "esh-mode" (&optional arg)) +(declare-function helm-quote-whitespace "helm-lib") +(declare-function eshell-skip-prompt "em-prompt") +(defvar eshell-special-chars-outside-quoting) + + +(defgroup helm-eshell nil + "Helm eshell completion and history." + :group 'helm) + + +(defcustom helm-eshell-fuzzy-match nil + "Enable fuzzy matching in `helm-esh-pcomplete' when non--nil." + :group 'helm-eshell + :type 'boolean) + + +(defvar helm-eshell-history-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "M-p") 'helm-next-line) + map) + "Keymap for `helm-eshell-history'.") + +(defvar helm-esh-completion-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "TAB") 'helm-next-line) + map) + "Keymap for `helm-esh-pcomplete'.") + +(defvar helm-eshell--quit-flag nil) + + +(defclass helm-esh-source (helm-source-sync) + ((init :initform (lambda () + (setq pcomplete-current-completions nil + pcomplete-last-completion-raw nil) + ;; Eshell-command add this hook in all minibuffers + ;; Remove it for the helm one. (Fixed in Emacs24) + (remove-hook 'minibuffer-setup-hook 'eshell-mode))) + (candidates :initform 'helm-esh-get-candidates) + ;(nomark :initform t) + (persistent-action :initform 'ignore) + (nohighlight :initform t) + (filtered-candidate-transformer + :initform + (lambda (candidates _sources) + (cl-loop + for i in candidates + collect + (cond ((string-match "\\`~/?" helm-ec-target) + (abbreviate-file-name i)) + ((string-match "\\`/" helm-ec-target) i) + (t + (file-relative-name i))) + into lst + finally return (sort lst 'helm-generic-sort-fn)))) + (action :initform 'helm-ec-insert)) + "Helm class to define source for Eshell completion.") + +;; Internal. +(defvar helm-ec-target "") +(defun helm-ec-insert (_candidate) + "Replace text at point with CANDIDATE. +The function that call this should set `helm-ec-target' to thing at point." + (set (make-local-variable 'comint-file-name-quote-list) + eshell-special-chars-outside-quoting) + (let ((pt (point))) + (when (and helm-ec-target + (search-backward helm-ec-target nil t) + (string= (buffer-substring (point) pt) helm-ec-target)) + (delete-region (point) pt))) + (when (string-match "\\`\\*" helm-ec-target) (insert "*")) + (let ((marked (helm-marked-candidates))) + (prog1 t ;; Makes helm returns t on action. + (insert + (mapconcat + (lambda (x) + (cond ((string-match "\\`~/" helm-ec-target) + ;; Strip out the first escape char added by + ;; `comint-quote-filename' before "~" (Issue #1803). + (substring (comint-quote-filename (abbreviate-file-name x)) 1)) + ((string-match "\\`/" helm-ec-target) + (comint-quote-filename x)) + (t + (concat (and (string-match "\\`[.]/" helm-ec-target) "./") + (comint-quote-filename + (file-relative-name x)))))) + marked " ") + (or (helm-aand (car (last marked)) + (string-match-p "/\\'" it) + "") + " "))))) + +(defun helm-esh-get-candidates () + "Get candidates for eshell completion using `pcomplete'." + (catch 'pcompleted + (with-helm-current-buffer + (let* ((pcomplete-stub) + pcomplete-seen pcomplete-norm-func + pcomplete-args pcomplete-last pcomplete-index + (pcomplete-autolist pcomplete-autolist) + (pcomplete-suffix-list pcomplete-suffix-list) + (table (pcomplete-completions)) + (entry (or (try-completion helm-pattern + (pcomplete-entries)) + helm-pattern))) + (cl-loop ;; expand entry too to be able to compare it with file-cand. + with exp-entry = (and (stringp entry) + (not (string= entry "")) + (file-name-as-directory + (expand-file-name entry default-directory))) + with comps = (all-completions pcomplete-stub table) + unless comps return (prog1 nil + ;; Don't add final space when + ;; there is no completion (issue #1990). + (setq helm-eshell--quit-flag t) + (message "No completions of %s" pcomplete-stub)) + for i in comps + ;; Transform the related names to abs names. + for file-cand = (and exp-entry + (if (file-remote-p i) i + (expand-file-name + i (file-name-directory entry)))) + ;; Compare them to avoid dups. + for file-entry-p = (and (stringp exp-entry) + (stringp file-cand) + ;; Fix :/tmp/foo/ $ cd foo + (not (file-directory-p file-cand)) + (file-equal-p exp-entry file-cand)) + if (and file-cand (or (file-remote-p file-cand) + (file-exists-p file-cand)) + (not file-entry-p)) + collect file-cand into ls + else + ;; Avoid adding entry here. + unless file-entry-p collect i into ls + finally return + (if (and exp-entry + (file-directory-p exp-entry) + ;; If the car of completion list is + ;; an executable, probably we are in + ;; command completion, so don't add a + ;; possible file related entry here. + (and ls (not (executable-find (car ls)))) + ;; Don't add entry if already in prompt. + (not (file-equal-p exp-entry pcomplete-stub))) + (append (list exp-entry) + ;; Entry should not be here now but double check. + (remove entry ls)) + ls)))))) + +;;; Eshell history. +;; +;; +(defclass helm-eshell-history-source (helm-source-sync) + ((init :initform + (lambda () + ;; Same comment as in `helm-source-esh'. + (remove-hook 'minibuffer-setup-hook 'eshell-mode))) + (candidates + :initform + (lambda () + (with-helm-current-buffer + (cl-loop for c from 0 to (ring-length eshell-history-ring) + collect (eshell-get-history c))))) + (nomark :initform t) + (multiline :initform t) + (keymap :initform helm-eshell-history-map) + (candidate-number-limit :initform 9999) + (action :initform (lambda (candidate) + (eshell-kill-input) + (insert candidate)))) + "Helm class to define source for Eshell history.") + + +;;;###autoload +(defun helm-esh-pcomplete () + "Preconfigured helm to provide helm completion in eshell." + (interactive) + (let* ((helm-quit-if-no-candidate t) + (helm-execute-action-at-once-if-one t) + (end (point-marker)) + (beg (save-excursion (eshell-bol) (point))) + (args (catch 'eshell-incomplete + (eshell-parse-arguments beg end))) + (target + (or (and (looking-back " " (1- (point))) " ") + (buffer-substring-no-properties + (save-excursion + (eshell-backward-argument 1) (point)) + end))) + (users-comp (string= target "~")) + (first (car args)) ; Maybe lisp delimiter "(". + last ; Will be the last but parsed by pcomplete. + del-space + del-dot) + (setq helm-ec-target (or target " ") + end (point) + ;; Reset beg for `with-helm-show-completion'. + beg (or (and target (not (string= target " ")) + (- end (length target))) + ;; Nothing at point. + (progn (insert " ") (setq del-space t) (point)))) + (when (string-match "\\`[~.]*.*/[.]\\'" target) + ;; Fix completion on + ;; "~/.", "~/[...]/.", and "../." + (delete-char -1) (setq del-dot t) + (setq helm-ec-target (substring helm-ec-target 0 (1- (length helm-ec-target))))) + (cond ((eq first ?\() + (helm-lisp-completion-or-file-name-at-point)) + ;; In eshell `pcomplete-parse-arguments' is called + ;; with `pcomplete-parse-arguments-function' + ;; locally bound to `eshell-complete-parse-arguments' + ;; which is calling `lisp-complete-symbol', + ;; calling it before would popup the + ;; *completions* buffer. + (t (setq last (replace-regexp-in-string + "\\`\\*" "" + (car (last (ignore-errors + (pcomplete-parse-arguments)))))) + ;; Set helm-eshell--quit-flag to non-nil only on + ;; quit, this tells to not add final suffix when quitting + ;; helm. + (add-hook 'helm-quit-hook 'helm-eshell--quit-hook-fn) + (with-helm-show-completion beg end + (unwind-protect + (or (helm :sources (helm-make-source "Eshell completions" 'helm-esh-source + :fuzzy-match helm-eshell-fuzzy-match) + :buffer "*helm pcomplete*" + :keymap helm-esh-completion-map + :resume 'noresume + :input (if (and (stringp last) + (not (string= last "")) + (not users-comp) + ;; Fix completion on + ;; "../" see #1832. + (or (file-exists-p last) + (helm-aand + (file-name-directory last) + (file-directory-p it)))) + (if (and (file-directory-p last) + (string-match "\\`[~.]*.*/[.]\\'" target)) + ;; Fix completion on + ;; "~/.", "~/[...]/.", and "../." + (expand-file-name + (concat (helm-basedir (file-name-as-directory last)) + (regexp-quote (helm-basename target)))) + (expand-file-name last)) + ;; Don't add "~" to input to + ;; provide completion on all + ;; users instead of only on + ;; current $HOME (#1832). + (unless users-comp last))) + ;; Delete removed dot on quit + (and del-dot (prog1 t (insert "."))) + ;; A space is needed to have completion, remove + ;; it when nothing found. + (and del-space (looking-back "\\s-" (1- (point))) + (delete-char -1)) + (if (and (null helm-eshell--quit-flag) + (and (stringp last) (file-directory-p last)) + (looking-back "\\([.]\\{1,2\\}\\|[^/]\\)\\'" + (1- (point)))) + (prog1 t (insert "/")) + ;; We need another flag for space here, but + ;; global to pass it to `helm-quit-hook', this + ;; space is added when point is just after + ;; previous completion and there is no + ;; more completion, see issue #1832. + (unless (or helm-eshell--quit-flag + (looking-back "/\\'" (1- (point)))) + (prog1 t (insert " "))) + (when (and helm-eshell--quit-flag + (string-match-p "[.]\\{2\\}\\'" last)) + (insert "/")))) + (remove-hook 'helm-quit-hook 'helm-eshell--quit-hook-fn) + (setq helm-eshell--quit-flag nil))))))) + +(defun helm-eshell--quit-hook-fn () + (setq helm-eshell--quit-flag t)) + +;;;###autoload +(defun helm-eshell-history () + "Preconfigured helm for eshell history." + (interactive) + (let* ((end (point)) + (beg (save-excursion (eshell-bol) (point))) + (input (buffer-substring beg end)) + flag-empty) + (when (eq beg end) + (insert " ") + (setq flag-empty t) + (setq end (point))) + (unwind-protect + (with-helm-show-completion beg end + (helm :sources (helm-make-source "Eshell history" + 'helm-eshell-history-source + :fuzzy-match helm-eshell-fuzzy-match) + :buffer "*helm eshell history*" + :resume 'noresume + :input input)) + (when (and flag-empty + (looking-back " " (1- (point)))) + (delete-char -1))))) + + +;;; Eshell prompts +;; +(defface helm-eshell-prompts-promptidx + '((t (:foreground "cyan"))) + "Face used to highlight Eshell prompt index." + :group 'helm-eshell-faces) + +(defface helm-eshell-prompts-buffer-name + '((t (:foreground "green"))) + "Face used to highlight Eshell buffer name." + :group 'helm-eshell-faces) + +(defcustom helm-eshell-prompts-promptidx-p t + "Show prompt number." + :group 'helm-eshell + :type 'boolean) + +(defvar helm-eshell-prompts-keymap + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "C-c o") 'helm-eshell-prompts-other-window) + (define-key map (kbd "C-c C-o") 'helm-eshell-prompts-other-frame) + map) + "Keymap for `helm-eshell-prompt-all'.") + +(defvar eshell-prompt-regexp) +(defvar eshell-highlight-prompt) + +(defun helm-eshell-prompts-list (&optional buffer) + "List the prompts in Eshell BUFFER. + +Return a list of (\"prompt\" (point) (buffer-name) prompt-index)) +e.g. (\"ls\" 162 \"*eshell*\" 3). +If BUFFER is nil, use current buffer." + (with-current-buffer (or buffer (current-buffer)) + (when (eq major-mode 'eshell-mode) + (save-excursion + (goto-char (point-min)) + (let (result (count 1)) + (helm-awhile (re-search-forward eshell-prompt-regexp nil t) + (when (or (and eshell-highlight-prompt + (get-text-property (match-beginning 0) 'read-only)) + (null eshell-highlight-prompt)) + (push (list (buffer-substring-no-properties + it (point-at-eol)) + it (buffer-name) count) + result) + (setq count (1+ count)))) + (nreverse result)))))) + +(defun helm-eshell-prompts-list-all () + "List the prompts of all Eshell buffers. +See `helm-eshell-prompts-list'." + (cl-loop for b in (buffer-list) + append (helm-eshell-prompts-list b))) + +(defun helm-eshell-prompts-transformer (candidates &optional all) + ;; ("ls" 162 "*eshell*" 3) => ("*eshell*:3:ls" . ("ls" 162 "*eshell*" 3)) + (cl-loop for (prt pos buf id) in candidates + collect `(,(concat + (when all + (concat (propertize + buf + 'face 'helm-eshell-prompts-buffer-name) + ":")) + (when helm-eshell-prompts-promptidx-p + (concat (propertize + (number-to-string id) + 'face 'helm-eshell-prompts-promptidx) + ":")) + prt) + . ,(list prt pos buf id)))) + +(defun helm-eshell-prompts-all-transformer (candidates) + (helm-eshell-prompts-transformer candidates t)) + +(cl-defun helm-eshell-prompts-goto (candidate &optional (action 'switch-to-buffer)) + ;; Candidate format: ("ls" 162 "*eshell*" 3) + (let ((buf (nth 2 candidate))) + (unless (and (string= (buffer-name) buf) + (eq action 'switch-to-buffer)) + (funcall action buf)) + (goto-char (nth 1 candidate)) + (recenter))) + +(defun helm-eshell-prompts-goto-other-window (candidate) + (helm-eshell-prompts-goto candidate 'switch-to-buffer-other-window)) + +(defun helm-eshell-prompts-goto-other-frame (candidate) + (helm-eshell-prompts-goto candidate 'switch-to-buffer-other-frame)) + +(defun helm-eshell-prompts-other-window () + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-eshell-prompts-goto-other-window))) +(put 'helm-eshell-prompts-other-window 'helm-only t) + +(defun helm-eshell-prompts-other-frame () + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-eshell-prompts-goto-other-frame))) +(put 'helm-eshell-prompts-other-frame 'helm-only t) + +;;;###autoload +(defun helm-eshell-prompts () + "Pre-configured `helm' to browse the prompts of the current Eshell." + (interactive) + (if (eq major-mode 'eshell-mode) + (helm :sources + (helm-build-sync-source "Eshell prompts" + :candidates (helm-eshell-prompts-list) + :candidate-transformer 'helm-eshell-prompts-transformer + :action '(("Go to prompt" . helm-eshell-prompts-goto))) + :buffer "*helm Eshell prompts*") + (message "Current buffer is not an Eshell buffer"))) + +;;;###autoload +(defun helm-eshell-prompts-all () + "Pre-configured `helm' to browse the prompts of all Eshell sessions." + (interactive) + (helm :sources + (helm-build-sync-source "All Eshell prompts" + :candidates (helm-eshell-prompts-list-all) + :candidate-transformer 'helm-eshell-prompts-all-transformer + :action '(("Go to prompt" . helm-eshell-prompts-goto) + ("Go to prompt in other window `C-c o`" . + helm-eshell-prompts-goto-other-window) + ("Go to prompt in other frame `C-c C-o`" . + helm-eshell-prompts-goto-other-frame)) + :keymap helm-eshell-prompts-keymap) + :buffer "*helm Eshell all prompts*")) + +(provide 'helm-eshell) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-eshell ends here diff --git a/elpa/helm-20191031.839/helm-eval.el b/elpa/helm-20191031.839/helm-eval.el new file mode 100644 index 00000000..caa31020 --- /dev/null +++ b/elpa/helm-20191031.839/helm-eval.el @@ -0,0 +1,204 @@ +;;; helm-eval.el --- eval expressions from helm. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: +(require 'cl-lib) +(require 'helm) +(require 'helm-help) +(require 'eldoc) +(require 'edebug) + + +(defgroup helm-eval nil + "Eval related Applications and libraries for Helm." + :group 'helm) + +(defcustom helm-eldoc-in-minibuffer-show-fn + 'helm-show-info-in-mode-line + "A function to display eldoc info. +Should take one arg: the string to display." + :group 'helm-eval + :type 'symbol) + +(defcustom helm-show-info-in-mode-line-delay 12 + "Eldoc will show info in mode-line during this delay if user is idle." + :type 'integer + :group 'helm-eval) + + +;;; Eldoc compatibility between emacs-24 and emacs-25 +;; +(if (require 'elisp-mode nil t) ; emacs-25 + ;; Maybe the eldoc functions have been + ;; already aliased by eldoc-eval. + (cl-loop for (f . a) in '((eldoc-current-symbol . + elisp--current-symbol) + (eldoc-fnsym-in-current-sexp . + elisp--fnsym-in-current-sexp) + (eldoc-get-fnsym-args-string . + elisp-get-fnsym-args-string) + (eldoc-get-var-docstring . + elisp-get-var-docstring)) + unless (fboundp f) + do (defalias f a)) + ;; Emacs-24. + (declare-function eldoc-current-symbol "eldoc") + (declare-function eldoc-get-fnsym-args-string "eldoc" (sym &optional index)) + (declare-function eldoc-get-var-docstring "eldoc" (sym)) + (declare-function eldoc-fnsym-in-current-sexp "eldoc")) + +;;; Evaluation Result +;; +;; +;; Internal +(defvar helm-eldoc-active-minibuffers-list nil) + +(defvar helm-eval-expression-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "") 'helm-eval-new-line-and-indent) + (define-key map (kbd "") 'lisp-indent-line) + (define-key map (kbd "") 'helm-lisp-completion-at-point) + (define-key map (kbd "C-p") 'previous-line) + (define-key map (kbd "C-n") 'next-line) + (define-key map (kbd "") 'previous-line) + (define-key map (kbd "") 'next-line) + (define-key map (kbd "") 'forward-char) + (define-key map (kbd "") 'backward-char) + map)) + +(defun helm-build-evaluation-result-source () + (helm-build-dummy-source "Evaluation Result" + :multiline t + :mode-line "C-RET: nl-and-indent, M-tab: reindent, C-tab:complete, C-p/n: next/prec-line." + :filtered-candidate-transformer (lambda (_candidates _source) + (list + (condition-case nil + (with-helm-current-buffer + (pp-to-string + (if edebug-active + (edebug-eval-expression + (read helm-pattern)) + (eval (read helm-pattern))))) + (error "Error")))) + :nohighlight t + :keymap helm-eval-expression-map + :action '(("Copy result to kill-ring" . (lambda (candidate) + (kill-new + (replace-regexp-in-string + "\n" "" candidate)) + (message "Result copied to kill-ring"))) + ("copy sexp to kill-ring" . (lambda (_candidate) + (kill-new helm-input) + (message "Sexp copied to kill-ring")))))) + +(defun helm-eval-new-line-and-indent () + (interactive) + (newline) (lisp-indent-line)) + +(defun helm-eldoc-store-minibuffer () + "Store minibuffer buffer name in `helm-eldoc-active-minibuffers-list'." + (with-selected-window (minibuffer-window) + (push (current-buffer) helm-eldoc-active-minibuffers-list))) + +(defun helm-eldoc-show-in-eval () + "Return eldoc in mode-line for current minibuffer input." + (let ((buf (window-buffer (active-minibuffer-window)))) + (condition-case err + (when (member buf helm-eldoc-active-minibuffers-list) + (with-current-buffer buf + (let* ((sym (save-excursion + (unless (looking-back ")\\|\"" (1- (point))) + (forward-char -1)) + (eldoc-current-symbol))) + (info-fn (eldoc-fnsym-in-current-sexp)) + (doc (or (eldoc-get-var-docstring sym) + (eldoc-get-fnsym-args-string + (car info-fn) (cadr info-fn))))) + (when doc (funcall helm-eldoc-in-minibuffer-show-fn doc))))) + (error (message "Eldoc in minibuffer error: %S" err) nil)))) + +(defun helm-show-info-in-mode-line (str) + "Display string STR in mode-line." + (save-selected-window + (with-current-buffer helm-buffer + (let ((mode-line-format (concat " " str))) + (force-mode-line-update) + (sit-for helm-show-info-in-mode-line-delay)) + (force-mode-line-update)))) + +;;; Calculation Result +;; +;; +(defvar helm-source-calculation-result + (helm-build-dummy-source "Calculation Result" + :filtered-candidate-transformer (lambda (_candidates _source) + (list + (condition-case nil + (calc-eval helm-pattern) + (error "error")))) + :nohighlight t + :action '(("Copy result to kill-ring" . (lambda (candidate) + (kill-new candidate) + (message "Result \"%s\" copied to kill-ring" + candidate))) + ("Copy operation to kill-ring" . (lambda (_candidate) + (kill-new helm-input) + (message "Calculation copied to kill-ring")))))) + +;;;###autoload +(defun helm-eval-expression (arg) + "Preconfigured helm for `helm-source-evaluation-result'." + (interactive "P") + (helm :sources (helm-build-evaluation-result-source) + :input (when arg (thing-at-point 'sexp)) + :buffer "*helm eval*" + :echo-input-in-header-line nil + :history 'read-expression-history)) + +(defvar eldoc-idle-delay) +;;;###autoload +(defun helm-eval-expression-with-eldoc () + "Preconfigured helm for `helm-source-evaluation-result' with `eldoc' support." + (interactive) + (let ((timer (run-with-idle-timer + eldoc-idle-delay 'repeat + 'helm-eldoc-show-in-eval))) + (unwind-protect + (minibuffer-with-setup-hook + 'helm-eldoc-store-minibuffer + (call-interactively 'helm-eval-expression)) + (and timer (cancel-timer timer)) + (setq helm-eldoc-active-minibuffers-list + (cdr helm-eldoc-active-minibuffers-list))))) + +;;;###autoload +(defun helm-calcul-expression () + "Preconfigured helm for `helm-source-calculation-result'." + (interactive) + (helm :sources 'helm-source-calculation-result + :buffer "*helm calcul*")) + +(provide 'helm-eval) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-eval.el ends here diff --git a/elpa/helm-20191031.839/helm-external.el b/elpa/helm-20191031.839/helm-external.el new file mode 100644 index 00000000..e539cde4 --- /dev/null +++ b/elpa/helm-20191031.839/helm-external.el @@ -0,0 +1,213 @@ +;;; helm-external.el --- Run Externals commands within Emacs with helm completion. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'cl-lib) +(require 'helm) +(require 'helm-help) +(require 'helm-net) + + +(defgroup helm-external nil + "External related Applications and libraries for Helm." + :group 'helm) + +(defcustom helm-raise-command nil + "A shell command to jump to a window running specific program. +Need external program wmctrl. +This will be use with `format', so use something like \"wmctrl -xa %s\"." + :type 'string + :group 'helm-external) + +(defcustom helm-external-programs-associations nil + "Alist to store externals programs associated with file extension. +This variable overhide setting in .mailcap file. +e.g : '\(\(\"jpg\" . \"gqview\"\) (\"pdf\" . \"xpdf\"\)\) " + :type '(alist :key-type string :value-type string) + :group 'helm-external) + +(defcustom helm-default-external-file-browser "nautilus" + "Default external file browser for your system. +Directories will be opened externally with it when +opening file externally in `helm-find-files'. +Set to nil if you do not have external file browser +or do not want to use it. +Windows users should set that to \"explorer.exe\"." + :group 'helm-external + :type 'string) + + +;;; Internals +(defvar helm-external-command-history nil) +(defvar helm-external-commands-list nil + "A list of all external commands the user can execute. +If this variable is not set by the user, it will be calculated +automatically.") + +(defun helm-external-commands-list-1 (&optional sort) + "Returns a list of all external commands the user can execute. +If `helm-external-commands-list' is non-nil it will +return its contents. Else it calculates all external commands +and sets `helm-external-commands-list'." + (helm-aif helm-external-commands-list + it + (setq helm-external-commands-list + (cl-loop + for dir in (split-string (getenv "PATH") path-separator) + when (and (file-exists-p dir) (file-accessible-directory-p dir)) + for lsdir = (cl-loop for i in (directory-files dir t) + for bn = (file-name-nondirectory i) + when (and (not (member bn completions)) + (not (file-directory-p i)) + (file-executable-p i)) + collect bn) + append lsdir into completions + finally return + (if sort (sort completions 'string-lessp) completions))))) + +(defun helm-run-or-raise (exe &optional file) + "Run asynchronously EXE or jump to the application window. +If EXE is already running just jump to his window if `helm-raise-command' +is non--nil. +When FILE argument is provided run EXE with FILE." + (let* ((real-com (car (split-string exe))) + (proc (if file (concat real-com " " file) real-com)) + process-connection-type) + (if (get-process proc) + (if helm-raise-command + (shell-command (format helm-raise-command real-com)) + (error "Error: %s is already running" real-com)) + (when (member real-com helm-external-commands-list) + (message "Starting %s..." real-com) + (if file + (start-process-shell-command + proc nil (format "%s %s" + real-com + (shell-quote-argument + (if (eq system-type 'windows-nt) + (helm-w32-prepare-filename file) + (expand-file-name file))))) + (start-process-shell-command proc nil real-com)) + (set-process-sentinel + (get-process proc) + (lambda (process event) + (when (and (string= event "finished\n") + helm-raise-command + (not (helm-get-pid-from-process-name real-com))) + (shell-command (format helm-raise-command "emacs"))) + (message "%s process...Finished." process)))) + (setq helm-external-commands-list + (cons real-com + (delete real-com helm-external-commands-list)))))) + +(defun helm-get-mailcap-for-file (filename) + "Get the command to use for FILENAME from mailcap files." + (mailcap-parse-mailcaps) + (let* ((ext (file-name-extension filename)) + (mime (when ext (mailcap-extension-to-mime ext))) + (result (when mime (mailcap-mime-info mime)))) + ;; If elisp file have no associations in .mailcap + ;; `mailcap-maybe-eval' is returned, in this case just return nil. + (when (stringp result) (helm-basename result)))) + +(defun helm-get-default-program-for-file (filename) + "Try to find a default program to open FILENAME. +Try first in `helm-external-programs-associations' and then in mailcap file +if nothing found return nil." + (let* ((ext (file-name-extension filename)) + (def-prog (assoc-default ext helm-external-programs-associations))) + (cond ((and def-prog (not (string= def-prog ""))) def-prog) + ((and helm-default-external-file-browser (file-directory-p filename)) + helm-default-external-file-browser) + (t (helm-get-mailcap-for-file filename))))) + +(defun helm-open-file-externally (file) + "Open FILE with an external program. +Try to guess which program to use with `helm-get-default-program-for-file'. +If not found or a prefix arg is given query the user which tool to use." + (let* ((fname (expand-file-name file)) + (collection (helm-external-commands-list-1 'sort)) + (def-prog (helm-get-default-program-for-file fname)) + (program (if (or helm-current-prefix-arg (not def-prog)) + ;; Prefix arg or no default program. + (prog1 + (helm-comp-read + "Program: " collection + :must-match t + :name "Open file Externally" + :del-input nil + :history helm-external-command-history) + ;; Always prompt to set this program as default. + (setq def-prog nil)) + ;; No prefix arg or default program exists. + def-prog))) + (unless (or def-prog ; Association exists, no need to record it. + ;; Don't try to record non--filenames associations (e.g urls). + (not (file-exists-p fname))) + (when + (y-or-n-p + (format + "Do you want to make `%s' the default program for this kind of files? " + program)) + (helm-aif (assoc (file-name-extension fname) + helm-external-programs-associations) + (setq helm-external-programs-associations + (delete it helm-external-programs-associations))) + (push (cons (file-name-extension fname) + (helm-read-string + "Program (Add args maybe and confirm): " program)) + helm-external-programs-associations) + (customize-save-variable 'helm-external-programs-associations + helm-external-programs-associations))) + (helm-run-or-raise program file) + (setq helm-external-command-history + (cons program + (delete program + (cl-loop for i in helm-external-command-history + when (executable-find i) collect i)))))) + +;;;###autoload +(defun helm-run-external-command (program) + "Preconfigured `helm' to run External PROGRAM asyncronously from Emacs. +If program is already running exit with error. +You can set your own list of commands with +`helm-external-commands-list'." + (interactive (list + (helm-comp-read + "RunProgram: " + (helm-external-commands-list-1 'sort) + :must-match t + :del-input nil + :name "External Commands" + :history helm-external-command-history))) + (helm-run-or-raise program) + (setq helm-external-command-history + (cons program (delete program + (cl-loop for i in helm-external-command-history + when (executable-find i) collect i))))) + + +(provide 'helm-external) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-external ends here diff --git a/elpa/helm-20191031.839/helm-files.el b/elpa/helm-20191031.839/helm-files.el new file mode 100644 index 00000000..4263ae77 --- /dev/null +++ b/elpa/helm-20191031.839/helm-files.el @@ -0,0 +1,4861 @@ +;;; helm-files.el --- helm file browser and related. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'cl-lib) +(require 'helm) +(require 'helm-types) +(require 'helm-utils) +(require 'helm-grep) +(require 'helm-help) +(require 'helm-locate) +(require 'helm-tags) +(require 'helm-buffers) +(eval-when-compile + (require 'thingatpt) + (require 'ffap) + (require 'dired-aux) + (require 'dired-x) + (require 'tramp) + (require 'image-dired)) + +(declare-function find-library-name "find-func.el" (library)) +(declare-function w32-shell-execute "ext:w32fns.c" (operation document &optional parameters show-flag)) +(declare-function gnus-dired-attach "ext:gnus-dired.el" (files-to-attach)) +(declare-function image-dired-display-image "image-dired.el" (file &optional original-size)) +(declare-function image-dired-update-property "image-dired.el" (prop value)) +(declare-function eshell-read-aliases-list "em-alias") +(declare-function eshell-send-input "esh-mode" (&optional use-region queue-p no-newline)) +(declare-function eshell-kill-input "esh-mode") +(declare-function eshell-bol "esh-mode") +(declare-function eshell-reset "esh-mode.el") +(declare-function eshell/cd "em-dirs.el") +(declare-function eshell-next-prompt "em-prompt.el") +(declare-function eshell-quote-argument "esh-arg.el") +(declare-function helm-ls-git-ls "ext:helm-ls-git") +(declare-function helm-hg-find-files-in-project "ext:helm-ls-hg") +(declare-function helm-gid "helm-id-utils.el") +(declare-function helm-find-1 "helm-find") +(declare-function helm-get-default-program-for-file "helm-external") +(declare-function helm-open-file-externally "helm-external") + +(defvar recentf-list) +(defvar helm-mm-matching-method) +(defvar dired-async-mode) +(defvar org-directory) + +(defgroup helm-files nil + "Files applications and libraries for Helm." + :group 'helm) + +(defcustom helm-tramp-verbose 0 + "Just like `tramp-verbose' but specific to helm. +When set to 0 don't show tramp messages in helm. +If you want to have the default tramp messages set it to 3." + :type 'integer + :group 'helm-files) + +(defcustom helm-ff-auto-update-initial-value nil + "Auto update when only one candidate directory is matched. +Default value when starting `helm-find-files' is nil to not confuse +new users. +For a better experience with `helm-find-files' set this to non--nil +and use C- to toggle it." + :group 'helm-files + :type 'boolean) + +(defcustom helm-ff-history-max-length 100 + "Number of elements shown in `helm-find-files' history." + :group 'helm-files + :type 'integer) + +(defcustom helm-ff-fuzzy-matching t + "Enable fuzzy matching for `helm-find-files' when non--nil. +See `helm-ff--transform-pattern-for-completion' for more info." + :group 'helm-files + :type 'boolean) + +(defcustom helm-ff-exif-data-program "exiftran" + "Program used to extract exif data of an image file." + :group 'helm-files + :type 'string) + +(defcustom helm-ff-exif-data-program-args "-d" + "Arguments used for `helm-ff-exif-data-program'." + :group 'helm-files + :type 'string) + +(defcustom helm-ff-newfile-prompt-p t + "Whether Prompt or not when creating new file. +This set `ffap-newfile-prompt'." + :type 'boolean + :group 'helm-files) + +(defcustom helm-ff-avfs-directory "~/.avfs" + "The default avfs directory, usually '~/.avfs'. +When this is set you will be able to expand archive filenames with `C-j' +inside an avfs directory mounted with mountavfs. +See ." + :type 'string + :group 'helm-files) + +(defcustom helm-ff-file-compressed-list '("gz" "bz2" "zip" "7z") + "Minimal list of compressed files extension." + :type '(repeat (choice string)) + :group 'helm-files) + +(defcustom helm-ff-printer-list nil + "A list of available printers on your system. +When non--nil let you choose a printer to print file. +Otherwise when nil the variable `printer-name' will be used. +On Unix based systems (lpstat command needed) you don't need to set this, +`helm-ff-find-printers' will find a list of available printers for you." + :type '(repeat (choice string)) + :group 'helm-files) + +(defcustom helm-ff-transformer-show-only-basename t + "Show only basename of candidates in `helm-find-files'. +This can be toggled at anytime from `helm-find-files' with \ +\\\\[helm-ff-run-toggle-basename]." + :type 'boolean + :group 'helm-files) + +(defcustom helm-ff-signal-error-on-dot-files t + "Signal error when file is `.' or `..' on file deletion when non--nil. +Default is non--nil. +WARNING: Setting this to nil is unsafe and can cause deletion of a whole tree." + :group 'helm-files + :type 'boolean) + +(defcustom helm-ff-search-library-in-sexp nil + "Search for library in `require' and `declare-function' sexp." + :group 'helm-files + :type 'boolean) + +(defcustom helm-tooltip-hide-delay 25 + "Hide tooltips automatically after this many seconds." + :group 'helm-files + :type 'integer) + +(defcustom helm-ff-file-name-history-use-recentf nil + "Use `recentf-list' instead of `file-name-history' in `helm-find-files'." + :group 'helm-files + :type 'boolean) + +(defcustom helm-ff-skip-boring-files nil + "Non--nil to skip boring files. + +I.e. the files matching regexps in `helm-boring-file-regexp-list'. +This take effect in `helm-find-files' and file completion used by `helm-mode' +i.e `helm-read-file-name'. +Note that when non-nil this will slow down slightly `helm-find-files'." + :group 'helm-files + :type 'boolean) + +(defcustom helm-ff-skip-git-ignored-files nil + "Non--nil to skip git ignored files. + +This take effect only in `helm-find-files'. +Check is not done on remote files. +Note that when non-nil this will slow down slightly `helm-find-files'." + :group 'helm-files + :type 'boolean) + +(defcustom helm-ff-candidate-number-limit 5000 + "The `helm-candidate-number-limit' for `helm-find-files' and friends. +Note that when going one level up with `\\\\[helm-find-files-up-one-level]' +The length of directory will be used instead if it is higher than this +value, this to avoid failing to preselect the previous directory/file if +this one is situated lower than `helm-ff-candidate-number-limit' num +candidate." + :group 'helm-files + :type 'integer) + +(defcustom helm-ff-up-one-level-preselect t + "Always preselect previous directory when going one level up. + +When non nil `candidate-number-limit' source value is modified +dynamically when going one level up if the position of previous +candidate in its directory is > to `helm-ff-candidate-number-limit'. + +This can be helpful to disable this and reduce +`helm-ff-candidate-number-limit' if you often navigate across very +large directories." + :group 'helm-files + :type 'boolean) + +(defcustom helm-files-save-history-extra-sources + '("Find" "Locate" "Recentf" + "Files from Current Directory" "File Cache") + "Extras source that save candidate to `file-name-history'." + :group 'helm-files + :type '(repeat (choice string))) + +(defcustom helm-find-files-before-init-hook nil + "Hook that run before initialization of `helm-find-files'." + :group 'helm-files + :type 'hook) + +(defcustom helm-find-files-after-init-hook nil + "Hook that run after initialization of `helm-find-files'." + :group 'helm-files + :type 'hook) + +(defcustom helm-find-files-bookmark-prefix "Helm-find-files: " + "bookmark name prefix of `helm-find-files' sessions." + :group 'helm-files + :type 'string) + +(defcustom helm-ff-guess-ffap-filenames nil + "Use ffap to guess local filenames at point in `helm-find-files'. +This doesn't disable url or mail at point, see +`helm-ff-guess-ffap-urls' for this." + :group 'helm-files + :type 'boolean) + +(defcustom helm-ff-guess-ffap-urls t + "Use ffap to guess local urls at point in `helm-find-files'. +This doesn't disable guessing filenames at point, +see `helm-ff-guess-ffap-filenames' for this. +See also `ffap-url-unwrap-remote' that may override this variable." + :group 'helm-files + :type 'boolean) + +(defcustom helm-ff-no-preselect nil + "When non--nil `helm-find-files' starts at root of current directory." + :group 'helm-files + :type 'boolean) + +(defcustom helm-ff-allow-non-existing-file-at-point nil + "Use file-at-point as initial input in `helm-find-files' even if it doesn't exists." + :group 'helm-files + :type 'boolean) + +(defcustom helm-find-files-ignore-thing-at-point nil + "Use only `default-directory' as default input in `helm-find-files'. +I.e text under cursor in `current-buffer' is ignored. +Note that when non-nil you will be unable to complete filename at point +in `current-buffer'." + :group 'helm-files + :type 'boolean) + +(defcustom helm-substitute-in-filename-stay-on-remote nil + "Don't switch back to local filesystem when expanding pattern with / or ~/." + :group 'helm-files + :type 'boolean) + +(defcustom helm-ff-goto-first-real-dired-exceptions '(dired-goto-file) + "Dired commands that are allowed moving to first real candidate." + :group 'helm-files + :type '(repeat (choice symbol))) + +(defcustom helm-mounted-network-directories nil + "A list of directories used for mounting remotes filesystem. + +When nil `helm-file-on-mounted-network-p' always return nil otherwise +it checks if a file is in one of these directories. + +Remote filesystem are generally mounted with sshfs." + :group 'helm-files + :type '(repeat string)) + +(defcustom helm-browse-project-default-find-files-fn + (cond ((executable-find "rg") + #'helm-browse-project-rg-find-files) + ((executable-find "ag") + #'helm-browse-project-ag-find-files) + (t #'helm-browse-project-walk-directory)) + "The default function to retrieve files in a non-vc directory. + +A function that takes a directory name as only arg." + :group 'helm-files + :type 'function) + +(defcustom helm-ff-kill-or-find-buffer-fname-fn + #'helm-ff-kill-or-find-buffer-fname + "Default function used to expand non-directory filenames in `helm-find-files'. + +This variable will take effect only in `helm-find-files', it affects +the behavior of persistent-action on filenames and non-existing +filenames. + +The default is to expand filename on first hit on +\\\\[helm-execute-persistent-action], pop buffer in other +window on second hit and finally kill this buffer on third hit, this +is very handy to create several new buffers, or when navigating, show +quickly the buffer of file to see its contents briefly before killing +it and continue navigating. + +However some users may not want this, so to disable this behavior just +set this to `ignore' function. + +Of course you can also write your own function to do something else." + :group 'helm-files + :type 'function) + +(defcustom helm-modes-using-escaped-strings + '(eshell-mode shell-mode term-mode) + "Modes that requires string's insertion to be escaped." + :group 'helm-files + :type '(repeat symbol)) + +(defcustom helm-ff-allow-recursive-deletes nil + "when 'always don't prompt for recursive deletion of directories. +When nil, will ask for recursive deletion. +Note that when deleting multiple directories you can answer ! when +prompted to avoid beeing asked for next directories, so it is probably +better to not modify this variable." + :group 'helm-files + :type '(choice + (const :tag "Delete non-empty directories" t) + (const :tag "Confirm for each directory" nil))) + +(defcustom helm-ff-delete-files-function #'helm-delete-marked-files + "The function to use by default to delete files. + +Default is to delete files synchronously, other choice is to delete +files asynchronously. + +BE AWARE that when deleting async you will not be warned about +recursive deletion of directories, IOW non empty directories will be +deleted with no warnings in background!!! + +It is the function that will be used when using `\\\\[helm-ff-run-delete-file]' +from `helm-find-files'." + :group 'helm-files + :type '(choice (function :tag "Delete files synchronously." + helm-delete-marked-files) + (function :tag "Delete files asynchronously." + helm-delete-marked-files-async))) + +(defcustom helm-trash-remote-files nil + "Allow trashing remote files when non-nil. + +Trashing remote files with tramp doesn't work out of the box unless +'trash-cli' package is installed, it is why trashing remote files from +helm is disabled by default. + +Tramp is using external 'trash' command in its `delete-file' and +`delete-directory' handlers when using `delete-by-moving-to-trash', +which is documented nowhere in Emacs. + +If you want to enable this you will have to install the 'trash' command +on remote (and/or locally if you want to trash as root), on Ubuntu +based distribution it is 'trash-cli'." + :group 'helm-files + :type 'boolean) + +(defcustom helm-list-directory-function + (cl-case system-type + (gnu/linux #'helm-list-dir-external) + (berkeley-unix #'helm-list-dir-lisp) + (windows-nt #'helm-list-dir-lisp) + (t #'helm-list-dir-lisp)) + "The function used in `helm-find-files' to list remote directories. + +Actually helm provides two functions to do this: `helm-list-dir-lisp' +and `helm-list-dir-external'. + +Using `helm-list-dir-external' will provides a similar display to what +provided with local files i.e. colorized symlinks, executables files +etc... whereas using `helm-list-dir-lisp' will allow colorizing only +directories but is more portable. + +NOTE: `helm-list-dir-external' needs ls and awk as dependencies. +Also the ls version installed on the remote side should support the +same arguments as the GNU/ls version that are -A -1 -F -b and -Q. +So even if you are using a GNU/ls version locally and you want to +connect e.g. on a Freebsd server you may have failures due to the +incompatible ls version installed on remote server. +In such case use `helm-list-dir-lisp' which work everywhere but is +slower and less featured (only directories colorized)." + :type 'function + :group 'helm-files) + +(defcustom helm-ff-initial-sort-method nil + "Sort method to use when initially listing a directory. +Note that this doesn't affect the listing when matching inside the +directory (i.e. filenames)." + :group 'helm-files + :type '(choice + (const :tag "alphabetically" nil) + (const :tag "newest" newest) + (const :tag "size" size))) + +(defcustom helm-ff-rotate-image-program "exiftran" + "External program used to rotate images." + :group 'helm-files + :type '(choice + (const :tag "Mogrify" "mogrify") + (const :tag "Exiftran" "exiftran") + (const :tag "Jpegtran" "jpegtran"))) + +(defcustom helm-ff-rotate-image-switch '("-i") + "Options used with `helm-ff-rotate-image-program'. +If you are using Mogrify or Jpegtran mandatory option is \"-rotate\", +with Exiftran mandatory option is \"-i\"." + :group 'helm-files + :type '(repeat string)) + + +;;; Faces +;; +;; +(defgroup helm-files-faces nil + "Customize the appearance of helm-files." + :prefix "helm-" + :group 'helm-files + :group 'helm-faces) + +(defface helm-ff-prefix + '((t (:background "yellow" :foreground "black"))) + "Face used to prefix new file or url paths in `helm-find-files'." + :group 'helm-files-faces) + +(defface helm-ff-executable + '((t (:foreground "green"))) + "Face used for executable files in `helm-find-files'." + :group 'helm-files-faces) + +(defface helm-ff-suid + '((t (:background "red" :foreground "white"))) + "Face used for suid files in `helm-find-files'." + :group 'helm-files-faces) + +(defface helm-ff-directory + '((t (:foreground "DarkRed" :background "LightGray"))) + "Face used for directories in `helm-find-files'." + :group 'helm-files-faces) + +(defface helm-ff-dotted-directory + '((t (:foreground "black" :background "DimGray"))) + "Face used for dotted directories in `helm-find-files'." + :group 'helm-files-faces) + +(defface helm-ff-dotted-symlink-directory + '((t (:foreground "DarkOrange" :background "DimGray"))) + "Face used for dotted symlinked directories in `helm-find-files'." + :group 'helm-files-faces) + +(defface helm-ff-symlink + '((t :inherit font-lock-comment-face)) + "Face used for symlinks in `helm-find-files'." + :group 'helm-files-faces) + +(defface helm-ff-invalid-symlink + '((t (:foreground "black" :background "red"))) + "Face used for invalid symlinks in `helm-find-files'." + :group 'helm-files-faces) + +(defface helm-ff-denied + '((t (:foreground "red" :background "black"))) + "Face used for non accessible files in `helm-find-files'." + :group 'helm-files-faces) + +(defface helm-ff-file + '((t (:inherit font-lock-builtin-face))) + "Face used for file names in `helm-find-files'." + :group 'helm-files-faces) + +(defface helm-ff-truename + '((t (:inherit font-lock-string-face))) + "Face used for symlink truenames in `helm-find-files'." + :group 'helm-files-faces) + +(defface helm-ff-dirs + '((t (:inherit font-lock-function-name-face))) + "Face used for file names in recursive dirs completion in `helm-find-files'." + :group 'helm-files-faces) + +(defface helm-ff-socket + '((t (:foreground "DeepPink"))) + "Face used for socket files in `helm-find-files'." + :group 'helm-files-faces) + +(defface helm-ff-pipe + '((t (:foreground "yellow" :background "black"))) + "Face used for named pipes and character device files in `helm-find-files'." + :group 'helm-files-faces) + +(defface helm-history-deleted + '((t (:inherit helm-ff-invalid-symlink))) + "Face used for deleted files in `file-name-history'." + :group 'helm-files-faces) + +(defface helm-history-remote + '((t (:foreground "Indianred1"))) + "Face used for remote files in `file-name-history'." + :group 'helm-files-faces) + +(defface helm-delete-async-message + '((t (:foreground "yellow"))) + "Face used for mode-line message." + :group 'helm-files-faces) + +;;; Helm-find-files - The helm file browser. +;; +;; Keymaps + +(defvar helm-find-files-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "RET") 'helm-ff-RET) + (define-key map (kbd "C-]") 'helm-ff-run-toggle-basename) + (define-key map (kbd "C-x C-f") 'helm-ff-run-locate) + (define-key map (kbd "C-x C-d") 'helm-ff-run-browse-project) + (define-key map (kbd "C-x r m") 'helm-ff-bookmark-set) + (define-key map (kbd "C-x r b") 'helm-find-files-switch-to-bookmark) + (define-key map (kbd "C-x C-q") 'helm-ff-run-marked-files-in-dired) + (define-key map (kbd "C-s") 'helm-ff-run-grep) + (define-key map (kbd "M-g s") 'helm-ff-run-grep) + (define-key map (kbd "M-g p") 'helm-ff-run-pdfgrep) + (define-key map (kbd "M-g z") 'helm-ff-run-zgrep) + (define-key map (kbd "M-g a") 'helm-ff-run-grep-ag) + (define-key map (kbd "M-g g") 'helm-ff-run-git-grep) + (define-key map (kbd "M-g i") 'helm-ff-run-gid) + (define-key map (kbd "M-.") 'helm-ff-run-etags) + (define-key map (kbd "M-R") 'helm-ff-run-rename-file) + (define-key map (kbd "M-C") 'helm-ff-run-copy-file) + (define-key map (kbd "M-B") 'helm-ff-run-byte-compile-file) + (define-key map (kbd "M-L") 'helm-ff-run-load-file) + (define-key map (kbd "M-S") 'helm-ff-run-symlink-file) + (define-key map (kbd "M-Y") 'helm-ff-run-relsymlink-file) + (define-key map (kbd "M-H") 'helm-ff-run-hardlink-file) + (define-key map (kbd "M-D") 'helm-ff-run-delete-file) + (define-key map (kbd "M-K") 'helm-ff-run-kill-buffer-persistent) + (define-key map (kbd "M-T") 'helm-ff-run-touch-files) + (define-key map (kbd "C-c d") 'helm-ff-persistent-delete) + (define-key map (kbd "M-e") 'helm-ff-run-switch-to-eshell) + (define-key map (kbd "C-c i") 'helm-ff-run-complete-fn-at-point) + (define-key map (kbd "C-c o") 'helm-ff-run-switch-other-window) + (define-key map (kbd "C-c C-o") 'helm-ff-run-switch-other-frame) + (define-key map (kbd "C-c C-x") 'helm-ff-run-open-file-externally) + (define-key map (kbd "C-c C-v") 'helm-ff-run-preview-file-externally) + (define-key map (kbd "C-c X") 'helm-ff-run-open-file-with-default-tool) + (define-key map (kbd "M-!") 'helm-ff-run-eshell-command-on-file) + (define-key map (kbd "M-@") 'helm-ff-run-query-replace-fnames-on-marked) + (define-key map (kbd "M-%") 'helm-ff-run-query-replace) + (define-key map (kbd "C-M-%") 'helm-ff-run-query-replace-regexp) + (define-key map (kbd "C-c =") 'helm-ff-run-ediff-file) + (define-key map (kbd "M-=") 'helm-ff-run-ediff-merge-file) + (define-key map (kbd "M-p") 'helm-find-files-history) + (define-key map (kbd "C-c h") 'helm-ff-file-name-history) + (define-key map (kbd "M-i") 'helm-ff-properties-persistent) + (define-key map (kbd "C-}") 'helm-narrow-window) + (define-key map (kbd "C-{") 'helm-enlarge-window) + (define-key map (kbd "C-") 'helm-ff-run-toggle-auto-update) + (define-key map (kbd "C-c ") 'helm-ff-run-toggle-auto-update) + (define-key map (kbd "C-c C-a") 'helm-ff-run-mail-attach-files) + (define-key map (kbd "C-c p") 'helm-ff-run-print-file) + (define-key map (kbd "C-c /") 'helm-ff-run-find-sh-command) + ;; Next 2 have no effect if candidate is not an image file. + (define-key map (kbd "M-l") 'helm-ff-rotate-left-persistent) + (define-key map (kbd "M-r") 'helm-ff-rotate-right-persistent) + (define-key map (kbd "C-l") 'helm-find-files-up-one-level) + (define-key map (kbd "C-r") 'helm-find-files-down-last-level) + (define-key map (kbd "C-c r") 'helm-ff-run-find-file-as-root) + (define-key map (kbd "C-x C-v") 'helm-ff-run-find-alternate-file) + (define-key map (kbd "C-c @") 'helm-ff-run-insert-org-link) + (define-key map (kbd "S-") 'helm-ff-sort-alpha) + (define-key map (kbd "S-") 'helm-ff-sort-by-newest) + (define-key map (kbd "S-") 'helm-ff-sort-by-size) + (helm-define-key-with-subkeys map (kbd "DEL") ?\d 'helm-ff-delete-char-backward + '((C-backspace . helm-ff-run-toggle-auto-update) + ([C-c DEL] . helm-ff-run-toggle-auto-update)) + nil 'helm-ff-delete-char-backward--exit-fn) + (when (fboundp 'tab-bar-mode) + (define-key map (kbd "C-c C-t") 'helm-ff-find-file-other-tab)) + map) + "Keymap for `helm-find-files'.") + +(defvar helm-read-file-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "") 'helm-cr-empty-string) + (define-key map (kbd "M-RET") 'helm-cr-empty-string) + (define-key map (kbd "C-]") 'helm-ff-run-toggle-basename) + (define-key map (kbd "C-.") 'helm-find-files-up-one-level) + (define-key map (kbd "C-l") 'helm-find-files-up-one-level) + (define-key map (kbd "C-r") 'helm-find-files-down-last-level) + (define-key map (kbd "C-c h") 'helm-ff-file-name-history) + (define-key map (kbd "C-") 'helm-ff-run-toggle-auto-update) + (define-key map (kbd "C-c ") 'helm-ff-run-toggle-auto-update) + (helm-define-key-with-subkeys map (kbd "DEL") ?\d 'helm-ff-delete-char-backward + '((C-backspace . helm-ff-run-toggle-auto-update) + ([C-c DEL] . helm-ff-run-toggle-auto-update)) + nil 'helm-ff-delete-char-backward--exit-fn) + map) + "Keymap for `helm-read-file-name'.") + +(defcustom helm-ff-lynx-style-map nil + "Use arrow keys to navigate with `helm-find-files'. +Note that if you define this variable with `setq' your change will +have no effect, use customize instead." + :group 'helm-files + :type 'boolean + :set (lambda (var val) + (set var val) + (if val + (progn + (define-key helm-find-files-map (kbd "") 'helm-execute-persistent-action) + (define-key helm-find-files-map (kbd "") 'helm-find-files-up-one-level) + (define-key helm-read-file-map (kbd "") 'helm-execute-persistent-action) + (define-key helm-read-file-map (kbd "") 'helm-find-files-up-one-level)) + (define-key helm-find-files-map (kbd "") nil) + (define-key helm-find-files-map (kbd "") nil) + (define-key helm-read-file-map (kbd "") nil) + (define-key helm-read-file-map (kbd "") nil)))) + +(defcustom helm-ff-DEL-up-one-level-maybe nil + "Use DEL to maybe go up one level when non nil. + +Going up one level works only when pattern is a directory endings with +\"/\", otherwise this command delete char backward. + +When nil always delete char backward." + :group 'helm-files + :type 'boolean) + +;; Internal. +(defvar helm-find-files-doc-header " (\\\\[helm-find-files-up-one-level]: Go up one level)" + "*The doc that is inserted in the Name header of a find-files or dired source.") +(defvar helm-ff-auto-update-flag nil + "Internal, flag to turn on/off auto-update in `helm-find-files'. +Don't set it directly, use instead `helm-ff-auto-update-initial-value'.") +(defvar helm-ff-last-expanded nil + "Store last expanded directory or file.") +(defvar helm-ff-default-directory nil) +(defvar helm-ff-history nil) +(defvar helm-ff-cand-to-mark nil) +(defvar helm-ff-url-regexp + "\\`\\(news\\(post\\)?:\\|nntp:\\|mailto:\\|file:\\|\\(ftp\\|https?\\|telnet\\|gopher\\|www\\|wais\\):/?/?\\).*" + "Same as `ffap-url-regexp' but match earlier possible url.") +;; helm-tramp-file-name-regexp is based on old version of +;; tramp-file-name-regexp i.e. "\\`/\\([^[/:]+\\|[^/]+]\\):" but it +;; seems it is wrong and a simpler regexp is enough, let's try it and +;; watch out! +(defvar helm-tramp-file-name-regexp "\\`/\\([^/:|]+\\):") +(defvar helm-marked-buffer-name "*helm marked*") +(defvar helm-ff--auto-update-state nil) +(defvar helm-ff--deleting-char-backward nil) +(defvar helm-multi-files--toggle-locate nil) +(defvar helm-ff--move-to-first-real-candidate t) +(defvar helm-find-files--toggle-bookmark nil) +(defvar helm-ff--tramp-methods nil) +(defvar helm-ff--directory-files-hash (make-hash-table :test 'equal)) +(defvar helm-ff-history-buffer-name "*helm-find-files history*") + +;;; Helm-find-files +;; +;; +(defcustom helm-find-files-actions + (helm-make-actions + "Find File" 'helm-find-file-or-marked + "Find file in Dired" 'helm-point-file-in-dired + "View file" 'view-file + "Query replace fnames on marked `M-@'" 'helm-ff-query-replace-fnames-on-marked + "Marked files in dired `C-x C-q, C-u wdired'" 'helm-marked-files-in-dired + "Query replace contents on marked `M-%'" 'helm-ff-query-replace + "Query replace regexp contents on marked `C-M-%'" 'helm-ff-query-replace-regexp + "Attach file(s) to mail buffer `C-c C-a'" 'helm-ff-mail-attach-files + "Serial rename files" 'helm-ff-serial-rename + "Serial rename by symlinking files" 'helm-ff-serial-rename-by-symlink + "Serial rename by copying files" 'helm-ff-serial-rename-by-copying + "Open file with default tool" 'helm-open-file-with-default-tool + "Find file in hex dump" 'hexl-find-file + "Browse project `C-x C-d'" 'helm-ff-browse-project + "Complete at point `C-c i'" 'helm-insert-file-name-completion-at-point + "Insert as org link `C-c @'" 'helm-files-insert-as-org-link + "Find shell command `C-c /'" 'helm-ff-find-sh-command + "Add marked files to file-cache" 'helm-ff-cache-add-file + "Open file externally `C-c C-x, C-u to choose'" 'helm-open-file-externally + "Grep File(s) `C-s, C-u Recurse'" 'helm-find-files-grep + "Grep current directory with AG `M-g a, C-u select type'" 'helm-find-files-ag + "Git grep `M-g g, C-u from root'" 'helm-ff-git-grep + "Zgrep File(s) `M-g z, C-u Recurse'" 'helm-ff-zgrep + "Gid `M-g i'" 'helm-ff-gid + "Switch to Eshell `M-e'" 'helm-ff-switch-to-eshell + "Etags `M-., C-u reload tag file'" 'helm-ff-etags-select + "Eshell command on file(s) `M-!, C-u take all marked as arguments.'" + 'helm-find-files-eshell-command-on-file + "Find file as root `C-c r'" 'helm-find-file-as-root + "Find alternate file `C-x C-v'" 'find-alternate-file + "Ediff File `C-c ='" 'helm-find-files-ediff-files + "Ediff Merge File `M-='" 'helm-find-files-ediff-merge-files + (lambda () (format "Delete File(s)%s `M-D' (C-u reverse trash)" + (if (eq helm-ff-delete-files-function + 'helm-delete-marked-files-async) + " async" ""))) + 'helm-ff-delete-files + "Touch File(s) `M-T'" 'helm-ff-touch-files + "Copy file(s) `M-C, C-u to follow'" 'helm-find-files-copy + "Rename file(s) `M-R, C-u to follow'" 'helm-find-files-rename + "Backup files" 'helm-find-files-backup + "Symlink files(s) `M-S, C-u to follow'" 'helm-find-files-symlink + "Relsymlink file(s) `M-Y, C-u to follow'" 'helm-find-files-relsymlink + "Hardlink file(s) `M-H, C-u to follow'" 'helm-find-files-hardlink + "Find file other window `C-c o'" 'helm-find-files-other-window + "Find file other frame `C-c C-o'" 'find-file-other-frame + (lambda () (and (fboundp 'tab-bar-mode) + "Find file other tab `C-c C-t'")) + 'find-file-other-tab + "Print File `C-c p, C-u to refresh'" 'helm-ff-print + "Locate `C-x C-f, C-u to specify locate db'" 'helm-ff-locate) + "Actions for `helm-find-files'." + :group 'helm-files + :type '(alist :key-type string :value-type function)) + +(defvar helm-source-find-files nil + "The main source to browse files. +Should not be used among other sources.") + +(defclass helm-source-ffiles (helm-source-sync) + ((header-name + :initform (lambda (name) + (concat name (substitute-command-keys + helm-find-files-doc-header)))) + (init + :initform (lambda () + (setq helm-ff-auto-update-flag + helm-ff-auto-update-initial-value) + (setq helm-ff--auto-update-state + helm-ff-auto-update-flag) + (helm-set-local-variable 'bookmark-make-record-function + #'helm-ff-make-bookmark-record) + (require 'helm-external))) + (candidates :initform 'helm-find-files-get-candidates) + (filtered-candidate-transformer + :initform '((lambda (candidates _source) + (cl-loop for f in candidates + for ff = (helm-ff-filter-candidate-one-by-one f) + when ff collect ff)) + helm-ff-sort-candidates)) + (persistent-action-if :initform 'helm-find-files-persistent-action-if) + (persistent-help :initform "Hit1 Expand Candidate, Hit2 or (C-u) Find file") + (help-message :initform 'helm-ff-help-message) + (mode-line :initform (list "File(s)" helm-mode-line-string)) + (volatile :initform t) + (cleanup :initform 'helm-find-files-cleanup) + (migemo :initform t) + (nohighlight :initform t) + (keymap :initform helm-find-files-map) + (candidate-number-limit :initform 'helm-ff-candidate-number-limit) + (action-transformer + :initform 'helm-find-files-action-transformer) + (action :initform 'helm-find-files-actions) + (before-init-hook :initform 'helm-find-files-before-init-hook) + (after-init-hook :initform 'helm-find-files-after-init-hook) + (group :initform 'helm-files))) + +;; Bookmark handlers. +;; +(defun helm-ff-make-bookmark-record () + "The `bookmark-make-record-function' for `helm-find-files'." + (with-helm-buffer + `((filename . ,helm-ff-default-directory) + (presel . ,(helm-get-selection)) + (handler . helm-ff-bookmark-jump)))) + +(defun helm-ff-bookmark-jump (bookmark) + "bookmark handler for `helm-find-files'." + (let ((fname (bookmark-prop-get bookmark 'filename)) + (presel (bookmark-prop-get bookmark 'presel))) + ;; Force tramp connection with `file-directory-p' before lauching + ;; hff otherwise the directory name is inserted on top before + ;; tramp starts and display candidates. FNAME is here always a + ;; directory. + (when (file-directory-p fname) + (helm-find-files-1 fname (if helm-ff-transformer-show-only-basename + (concat "^" (regexp-quote (helm-basename presel))) + (regexp-quote presel)))))) + +(defun helm-ff-bookmark-set () + "Record `helm-find-files' session in bookmarks." + (interactive) + (with-helm-alive-p + (with-helm-buffer + (bookmark-set + (concat helm-find-files-bookmark-prefix + (abbreviate-file-name helm-ff-default-directory)))) + (message "Helm find files session bookmarked! "))) +(put 'helm-ff-bookmark-set 'helm-only t) + +(defcustom helm-dwim-target nil + "Default target directory for file actions. + +Define the directory where you want to start navigating for the target +directory when copying, renaming etc... You can use the +`default-directory' of `next-window', the current +`default-directory' or have completion on all the directories +belonging to each window." + :group 'helm-files + :type '(radio :tag "Define default target directory for file actions." + (const :tag "Directory belonging to next window" next-window) + (const :tag "Completion on directories belonging to each window" completion) + (const :tag "Use initial directory or `default-directory'" nil))) + +(defun helm-dwim-target-directory () + "Try to return a suitable directory according to `helm-dwim-target'." + (with-helm-current-buffer + (let* ((wins (remove (get-buffer-window helm-marked-buffer-name) + (window-list))) + (num-windows (length wins))) + (expand-file-name + (cond ((and (> num-windows 1) + (eq helm-dwim-target 'completion)) + (helm-comp-read "Browse target starting from: " + (append (list (or (car-safe helm-ff-history) + default-directory) + default-directory) + (cl-loop for w in wins collect + (with-selected-window w + default-directory))))) + ((and (> num-windows 1) + (eq helm-dwim-target 'next-window)) + (with-selected-window (next-window) + default-directory)) + ((or (= num-windows 1) + (null helm-dwim-target)) + ;; Using the car of *ff-history allow + ;; staying in the directory visited instead of + ;; current. + (or (car-safe helm-ff-history) default-directory))))))) + +(defun helm-ff--count-and-collect-dups (files) + (cl-loop with dups = (make-hash-table :test 'equal) + for f in files + for file = (if (file-directory-p f) + (concat (helm-basename f) "/") + (helm-basename f)) + for count = (gethash file dups) + if count do (puthash file (1+ count) dups) + else do (puthash file 1 dups) + finally return (cl-loop for k being the hash-keys in dups + using (hash-value v) + if (> v 1) + collect (format "%s(%s)" k v) + else + collect k))) + +(defun helm-find-files-do-action (action) + "Generic function for creating actions from `helm-source-find-files'. +ACTION must be an action supported by `helm-dired-action'." + (require 'dired-async) + (let* ((ifiles (mapcar 'expand-file-name ; Allow modify '/foo/.' -> '/foo' + (helm-marked-candidates :with-wildcard t))) + (cand (helm-get-selection)) ; Target + (prefarg helm-current-prefix-arg) + (prompt (format "%s %s file(s) %s: " + (if (and (and (fboundp 'dired-async-mode) + dired-async-mode) + (null prefarg)) + (concat "Async " (symbol-name action)) + (capitalize (symbol-name action))) + (length ifiles) + (if (memq action '(symlink relsymlink hardlink)) + "from" "to"))) + helm-ff--move-to-first-real-candidate + helm-display-source-at-screen-top ; prevent setting window-start. + helm-ff-auto-update-initial-value + ;; It is not possible to rename a file to a boring name when + ;; helm-ff-skip-boring-files is enabled + helm-ff-skip-boring-files + ;; If HFF is using a frame use a frame as well. + (helm-actions-inherit-frame-settings t) + helm-use-frame-when-more-than-two-windows + (dest (with-helm-display-marked-candidates + helm-marked-buffer-name + (helm-ff--count-and-collect-dups ifiles) + (with-helm-current-buffer + (helm-read-file-name + prompt + :preselect (unless (cdr ifiles) + (concat + "^" + (regexp-quote + (if helm-ff-transformer-show-only-basename + (helm-basename cand) cand)))) + :initial-input (helm-dwim-target-directory) + :history (helm-find-files-history nil :comp-read nil))))) + (dest-dir-p (file-directory-p dest)) + (dest-dir (helm-basedir dest))) + (unless (or dest-dir-p (file-directory-p dest-dir)) + (when (y-or-n-p (format "Create directory `%s'? " dest-dir)) + (make-directory dest-dir t))) + (helm-dired-action + dest :files ifiles :action action :follow prefarg))) + +(defun helm-find-files-copy (_candidate) + "Copy files from `helm-find-files'." + (helm-find-files-do-action 'copy)) + +(defun helm-find-files-backup (_candidate) + "Backup files from `helm-find-files'. +This reproduce the behavior of \"cp --backup=numbered from to\"." + (cl-assert (and (fboundp 'dired-async-mode) dired-async-mode) nil + "Backup only available when `dired-async-mode' is enabled") + (helm-find-files-do-action 'backup)) + +(defun helm-find-files-rename (_candidate) + "Rename files from `helm-find-files'." + (helm-find-files-do-action 'rename)) + +(defun helm-find-files-symlink (_candidate) + "Symlink files from `helm-find-files'." + (helm-find-files-do-action 'symlink)) + +(defun helm-find-files-relsymlink (_candidate) + "Relsymlink files from `helm-find-files'." + (helm-find-files-do-action 'relsymlink)) + +(defun helm-find-files-hardlink (_candidate) + "Hardlink files from `helm-find-files'." + (helm-find-files-do-action 'hardlink)) + +(defun helm-find-files-other-window (_candidate) + "Keep current-buffer and open files in separate windows. +When a prefix arg is detected files are opened in a vertical windows +layout." + (let* ((files (helm-marked-candidates)) + (buffers (mapcar 'find-file-noselect files))) + (helm-window-show-buffers buffers t))) + +(defun helm-find-files-byte-compile (_candidate) + "Byte compile elisp files from `helm-find-files'." + (let ((files (helm-marked-candidates :with-wildcard t)) + (parg helm-current-prefix-arg)) + (cl-loop for fname in files + do (byte-compile-file fname parg)))) + +(defun helm-find-files-load-files (_candidate) + "Load elisp files from `helm-find-files'." + (let ((files (helm-marked-candidates :with-wildcard t))) + (cl-loop for fname in files + do (load fname)))) + +(defun helm-find-files-ediff-files-1 (candidate &optional merge) + "Generic function to ediff/merge files in `helm-find-files'." + (let* ((helm-dwim-target 'next-window) + (bname (helm-basename candidate)) + (marked (helm-marked-candidates :with-wildcard t)) + (prompt (if merge "Ediff Merge `%s' With File: " + "Ediff `%s' With File: ")) + (fun (if merge 'ediff-merge-files 'ediff-files)) + (input (helm-dwim-target-directory)) + (presel (if helm-ff-transformer-show-only-basename + (helm-basename candidate) + (expand-file-name + (helm-basename candidate) + input)))) + (if (= (length marked) 2) + (funcall fun (car marked) (cadr marked)) + (funcall fun candidate (helm-read-file-name + (format prompt bname) + :initial-input input + :preselect presel))))) + +(defun helm-find-files-ediff-files (candidate) + (helm-find-files-ediff-files-1 candidate)) + +(defun helm-find-files-ediff-merge-files (candidate) + (helm-find-files-ediff-files-1 candidate 'merge)) + +(defun helm-find-files-grep (_candidate) + "Default action to grep files from `helm-find-files'." + (helm-do-grep-1 (helm-marked-candidates :with-wildcard t) + helm-current-prefix-arg)) + +(defun helm-ff-git-grep (_candidate) + "Default action to git-grep `helm-ff-default-directory'." + (helm-grep-git-1 helm-ff-default-directory helm-current-prefix-arg)) + +(defun helm-find-files-ag (_candidate) + (helm-grep-ag helm-ff-default-directory + helm-current-prefix-arg)) + +(defun helm-ff-zgrep (_candidate) + "Default action to zgrep files from `helm-find-files'." + (helm-ff-zgrep-1 (helm-marked-candidates :with-wildcard t) helm-current-prefix-arg)) + +(defun helm-ff-pdfgrep (_candidate) + "Default action to pdfgrep files from `helm-find-files'." + (let* ((recurse nil) + (cands (cl-loop for file in (helm-marked-candidates :with-wildcard t) + for dir = (file-directory-p file) + when dir do (setq recurse t) + when (or dir + (string= (file-name-extension file) "pdf") + (string= (file-name-extension file) "PDF")) + collect file))) + (when cands + (helm-do-pdfgrep-1 cands recurse)))) + +(defun helm-ff-etags-select (candidate) + "Default action to jump to etags from `helm-find-files'." + (when (get-buffer helm-action-buffer) + (kill-buffer helm-action-buffer)) + (let* ((source-name (assoc-default 'name (helm-get-current-source))) + (default-directory (if (string= source-name "Find Files") + helm-ff-default-directory + (file-name-directory candidate)))) + (helm-etags-select helm-current-prefix-arg))) + +(defvar eshell-command-aliases-list nil) +(defvar helm-eshell-command-on-file-input-history nil) +(cl-defun helm-find-files-eshell-command-on-file-1 (&optional map) + "Run `eshell-command' on CANDIDATE or marked candidates. +This is done possibly with an eshell alias, if no alias found, you can type in +an eshell command. + +Only aliases accepting a file as argument at the end of command line +are collected, i.e aliases ending with \"$1\" or \"$*\". + +Basename of CANDIDATE can be a wild-card. +e.g you can do \"eshell-command command *.el\" +Where \"*.el\" is the CANDIDATE. + +It is possible to do eshell-command command +like this: \"command %s some more args\". + +If MAP is given run `eshell-command' on all marked files at once, +Otherwise, run `eshell-command' on each marked files. +In other terms, with a prefix arg do on the three marked files +\"foo\" \"bar\" \"baz\": + +\"eshell-command command foo bar baz\" + +otherwise do + +\"eshell-command command foo\" +\"eshell-command command bar\" +\"eshell-command command baz\" + +Note: +You have to setup some aliases in eshell with the `alias' command or +by editing yourself the file `eshell-aliases-file' to make this +working." + (require 'em-alias) (eshell-read-aliases-list) + (when (or eshell-command-aliases-list + (y-or-n-p "No eshell aliases found, run eshell-command without alias anyway? ")) + (let* ((cand-list (helm-marked-candidates :with-wildcard t)) + (default-directory (or helm-ff-default-directory + ;; If candidate is an url *-ff-default-directory is nil + ;; so keep value of default-directory. + default-directory)) + helm-display-source-at-screen-top + (helm-actions-inherit-frame-settings t) + helm-use-frame-when-more-than-two-windows + (command (with-helm-display-marked-candidates + helm-marked-buffer-name + (helm-ff--count-and-collect-dups + (mapcar 'helm-basename cand-list)) + (with-helm-current-buffer + (helm-comp-read + "Command: " + (cl-loop for (a c) in (eshell-read-aliases-list) + ;; Positional arguments may be double + ;; quoted (Issue #1881). + when (string-match "[\"]?.*\\(\\$1\\|\\$\\*\\)[\"]?\\'" c) + collect (propertize a 'help-echo c) into ls + finally return (sort ls 'string<)) + :buffer "*helm eshell on file*" + :name "Eshell command" + :mode-line + '("Eshell alias" + "C-h m: Help, \\[universal-argument]: Insert output at point") + :help-message 'helm-esh-help-message + :input-history + 'helm-eshell-command-on-file-input-history)))) + (alias-value (car (assoc-default command eshell-command-aliases-list))) + cmd-line) + (if (or (equal helm-current-prefix-arg '(16)) + (equal map '(16))) + ;; Two time C-u from `helm-comp-read' mean print to current-buffer. + ;; i.e `eshell-command' will use this value. + (setq current-prefix-arg '(16)) + ;; Else reset the value of `current-prefix-arg' + ;; to avoid printing in current-buffer. + (setq current-prefix-arg nil)) + (if (and (or + ;; One prefix-arg have been passed before `helm-comp-read'. + ;; If map have been set with C-u C-u (value == '(16)) + ;; ignore it. + (and map (equal map '(4))) + ;; One C-u from `helm-comp-read'. + (equal helm-current-prefix-arg '(4)) + ;; An alias that finish with $* + (and alias-value + ;; If command is an alias be sure it accept + ;; more than one arg i.e $*. + (string-match "\\$\\*$" alias-value))) + (cdr cand-list)) + + ;; Run eshell-command with ALL marked files as arguments. + ;; This wont work on remote files, because tramp handlers depends + ;; on `default-directory' (limitation). + (let ((mapfiles (mapconcat 'eshell-quote-argument cand-list " "))) + (if (string-match "%s" command) + (setq cmd-line (format command mapfiles)) ; See [1] + (setq cmd-line (format "%s %s" command mapfiles))) + (eshell-command cmd-line)) + + ;; Run eshell-command on EACH marked files. + ;; To work with tramp handler we have to call + ;; COMMAND on basename of each file, using + ;; its basedir as `default-directory'. + (cl-loop for f in cand-list + for n from 1 + for dir = (and (not (string-match helm--url-regexp f)) + (helm-basedir f)) + ;; We can use basename here as the command will run + ;; under default-directory. + ;; This allow running e.g. "tar czvf test.tar.gz + ;; %s/*" without creating an archive expanding from /home. + for file = (eshell-quote-argument (helm-basename f)) + ;; \@ => placeholder for file without extension. + ;; \# => placeholder for incremental number. + for fcmd = (replace-regexp-in-string + "\\\\@" (regexp-quote (file-name-sans-extension file)) + (replace-regexp-in-string + "\\\\#" (format "%03d" n) command)) + for com = (if (string-match "%s" fcmd) + ;; [1] This allow to enter other args AFTER filename + ;; i.e + (format fcmd file) + (format "%s %s" fcmd file)) + do (let ((default-directory (or dir default-directory))) + (eshell-command com))))))) + +(defun helm-find-files-eshell-command-on-file (_candidate) + "Run `eshell-command' on CANDIDATE or marked candidates. +See `helm-find-files-eshell-command-on-file-1' for more info." + (helm-find-files-eshell-command-on-file-1 helm-current-prefix-arg)) + +(defun helm-ff-switch-to-eshell (_candidate) + "Switch to eshell and cd to `helm-ff-default-directory'. + +With a numeric prefix arg switch to numbered eshell buffer, if no +prefix arg provided and more than one eshell buffer exists, provide +completions on those buffers. If only one eshell buffer exists, +switch to this one, if no eshell buffer exists or if the numeric +prefix arg eshell buffer doesn't exists, create it and switch to it." + (let ((cd-eshell (lambda () + (eshell/cd helm-ff-default-directory) + (eshell-reset))) + (bufs (cl-loop for b in (mapcar 'buffer-name (buffer-list)) + when (helm-ff--eshell-interactive-buffer-p b) + collect b))) + (helm-aif (and (null helm-current-prefix-arg) + (if (cdr bufs) + (helm-comp-read "Switch to eshell buffer: " bufs + :must-match t) + (car bufs))) + (switch-to-buffer it) + (eshell helm-current-prefix-arg)) + (unless (get-buffer-process (current-buffer)) + (funcall cd-eshell)))) + +(defun helm-ff--eshell-interactive-buffer-p (buffer) + (with-current-buffer buffer + (and (eq major-mode 'eshell-mode) + (save-excursion + (goto-char (point-min)) + (eshell-next-prompt 1) + (null (eql (point) (point-min))))))) + +(defun helm-ff-touch-files (_candidate) + "The touch files action for helm-find-files." + (let* ((files (helm-marked-candidates)) + (split (cl-loop for f in files + for spt = (unless helm-current-prefix-arg + (cons (helm-basedir f) + (split-string f ", ?"))) + if spt + append (cl-loop with dir = (car spt) + for ff in (cdr spt) + collect (expand-file-name ff dir)) + else collect f)) + (timestamp (helm-comp-read + "Timestamp (default Now): " + (cl-loop for f in split + for time = (file-attributes f) + for date = (and time + (format-time-string + "%Y-%m-%d %H:%M:%S" + (nth 5 time))) + when date + collect (cons (format "%s: %s" + (helm-basename f) date) + date)) + :default + (format-time-string "%Y-%m-%d %H:%M:%S" + (current-time)))) + (failures + (cl-loop with default-directory = helm-ff-default-directory + for f in split + for file = (or (file-remote-p f 'localname) f) + when (> (process-file + "touch" nil nil nil "-d" timestamp file) + 0) + collect f))) + (when failures + (message "Failed to touch *%s files:\n%s" + (length failures) + (mapconcat (lambda (f) (format "- %s\n" f)) failures ""))))) + +(defun helm-ff-run-touch-files () + "Used to interactively run touch file action from keyboard." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-ff-touch-files))) +(put 'helm-ff-run-touch-files 'helm-only t) + +(defun helm-ff-sort-by-size () + (interactive) + (unless (eq helm-ff-initial-sort-method 'size) + (setq helm-ff-initial-sort-method 'size) + (helm-update (helm-get-selection nil helm-ff-transformer-show-only-basename))) + (message "Sorting by size")) +(put 'helm-ff-sort-by-size 'helm-only t) + +(defun helm-ff-sort-by-newest () + (interactive) + (unless (eq helm-ff-initial-sort-method 'newest) + (setq helm-ff-initial-sort-method 'newest) + (helm-update (helm-get-selection nil helm-ff-transformer-show-only-basename))) + (message "Sorting by newest")) +(put 'helm-ff-sort-by-newest 'helm-only t) + +(defun helm-ff-sort-alpha () + (interactive) + (unless (eq helm-ff-initial-sort-method nil) + (setq helm-ff-initial-sort-method nil) + (helm-update (helm-get-selection nil helm-ff-transformer-show-only-basename))) + (message "Sorting alphabetically")) +(put 'helm-ff-sort-alpha 'helm-only t) + +(defun helm-ff-serial-rename-action (method) + "Rename all marked files in `helm-ff-default-directory' with METHOD. +See `helm-ff-serial-rename-1'." + (let* ((helm--reading-passwd-or-string t) + (cands (helm-marked-candidates :with-wildcard t)) + (def-name (car cands)) + (name (helm-read-string "NewName: " + (replace-regexp-in-string + "[0-9]+$" "" + (helm-basename + def-name + (file-name-extension def-name))))) + (start (read-number "StartAtNumber: ")) + (extension (helm-read-string "Extension: " + (file-name-extension (car cands)))) + (dir (expand-file-name + (helm-read-file-name + "Serial Rename to directory: " + :initial-input + (expand-file-name helm-ff-default-directory) + :test 'file-directory-p + :must-match t))) + done) + (with-helm-display-marked-candidates + helm-marked-buffer-name (helm-ff--count-and-collect-dups cands) + (if (y-or-n-p + (format "Rename %s file(s) to <%s> like this ?\n%s " + (length cands) dir (format "%s <-> %s%s.%s" + (helm-basename (car cands)) + name start extension))) + (progn + (helm-ff-serial-rename-1 + dir cands name start extension :method method) + (setq done t) + (message nil)))) + (if done + (with-helm-current-buffer (helm-find-files-1 dir)) + (message "Operation aborted")))) + +(defun helm-ff-member-directory-p (file directory) + (let ((dir-file (expand-file-name + (file-name-as-directory (file-name-directory file)))) + (cur-dir (expand-file-name (file-name-as-directory directory)))) + (string= dir-file cur-dir))) + +(cl-defun helm-ff-serial-rename-1 + (directory collection new-name start-at-num extension &key (method 'rename)) + "rename files in COLLECTION to DIRECTORY with the prefix name NEW-NAME. +Rename start at number START-AT-NUM - ex: prefixname-01.jpg. +EXTENSION is the file extension to use, in empty prompt, +reuse the original extension of file. +METHOD can be one of rename, copy or symlink. +Files will be renamed if they are files of current directory, otherwise they +will be treated with METHOD. +Default METHOD is rename." + ;; Maybe remove directories selected by error in collection. + (setq collection (cl-remove-if 'file-directory-p collection)) + (let* ((tmp-dir (file-name-as-directory + (concat (file-name-as-directory directory) + (symbol-name (cl-gensym "tmp"))))) + (fn (cl-case method + (copy 'copy-file) + (symlink 'make-symbolic-link) + (rename 'rename-file) + (t (error "Error: Unknown method %s" method))))) + (make-directory tmp-dir) + (unwind-protect + (progn + ;; Rename all files to tmp-dir with new-name. + ;; If files are not from start directory, use method + ;; to move files to tmp-dir. + (cl-loop for i in collection + for count from start-at-num + for fnum = (if (< count 10) "0%s" "%s") + for nname = (concat tmp-dir new-name (format fnum count) + (if (not (string= extension "")) + (format ".%s" (replace-regexp-in-string + "[.]" "" extension)) + (file-name-extension i 'dot))) + do (if (helm-ff-member-directory-p i directory) + (rename-file i nname) + (funcall fn i nname))) + ;; Now move all from tmp-dir to destination. + (cl-loop with dirlist = (directory-files + tmp-dir t directory-files-no-dot-files-regexp) + for f in dirlist do + (if (file-symlink-p f) + (make-symbolic-link (file-truename f) + (concat (file-name-as-directory directory) + (helm-basename f))) + (rename-file f directory)))) + (delete-directory tmp-dir t)))) + +(defun helm-ff-serial-rename (_candidate) + "Serial rename all marked files to `helm-ff-default-directory'. +Rename only file of current directory, and symlink files coming from +other directories. +See `helm-ff-serial-rename-1'." + (helm-ff-serial-rename-action 'rename)) + +(defun helm-ff-serial-rename-by-symlink (_candidate) + "Serial rename all marked files to `helm-ff-default-directory'. +Rename only file of current directory, and symlink files coming from +other directories. +See `helm-ff-serial-rename-1'." + (helm-ff-serial-rename-action 'symlink)) + +(defun helm-ff-serial-rename-by-copying (_candidate) + "Serial rename all marked files to `helm-ff-default-directory'. +Rename only file of current directory, and copy files coming from +other directories. +See `helm-ff-serial-rename-1'." + (helm-ff-serial-rename-action 'copy)) + +(defvar helm-ff-query-replace-fnames-history-from nil) +(defvar helm-ff-query-replace-fnames-history-to nil) +(defun helm-ff-query-replace-on-filenames (candidates) + "Query replace on filenames of CANDIDATES. +This doesn't replace inside the files, only modify filenames." + (with-helm-display-marked-candidates + helm-marked-buffer-name + (mapcar 'helm-basename candidates) + (let* ((regexp (read-string "Replace regexp on filename(s): " + nil 'helm-ff-query-replace-history-from + (helm-basename (car candidates)))) + (rep (read-string (format "Replace regexp `%s' with: " regexp) + nil 'helm-ff-query-replace-history-to)) + subexp) + (cl-loop with query = "y" + with count = 0 + with target = nil + for old in candidates + for new = (concat (helm-basedir old) + (helm--replace-regexp-in-buffer-string + (save-match-data + (cond ((string= regexp "%.") + (setq subexp 1) + (helm-ff--prepare-str-with-regexp + (setq target (helm-basename old t)))) + ((string= regexp ".%") + (setq subexp 1) + (helm-ff--prepare-str-with-regexp + (setq target (file-name-extension old)))) + ((string= regexp "%") + (regexp-quote + (setq target (helm-basename old)))) + ((string-match "%:\\([0-9]+\\):\\([0-9]+\\)" regexp) + (setq subexp 1) + (let ((beg (match-string 1 regexp)) + (end (match-string 2 regexp)) + (str (helm-basename old))) + (setq target (substring str + (string-to-number beg) + (string-to-number end))) + (helm-ff--prepare-str-with-regexp str beg end))) + (t regexp))) + (save-match-data + (cond (;; Handle incremental + ;; replacement with \# in + ;; search and replace + ;; feature in placeholder \@. + (string-match + "\\\\@/\\(.*\\)/\\(\\(?99:.*\\)\\\\#\\)/" + rep) + (replace-regexp-in-string + (match-string 1 rep) + (concat (match-string 99 rep) + (format "%03d" (1+ count))) + target)) + ;; Incremental replacement + ;; before or after \@. + ((and (string-match-p "\\\\#" rep) + (string-match "\\\\@" rep)) + (replace-regexp-in-string + "\\\\#" (format "%03d" (1+ count)) + (replace-match target t t rep))) + ;; Simple incremental replacement. + ((string-match "\\\\#" rep) + (replace-match + (format "%03d" (1+ count)) t t rep)) + ;; Substring replacement in placeholder. + ((string-match + "\\\\@:\\([0-9]*\\):\\([0-9]*\\)" rep) + (replace-match (substring + target + (string-to-number + (match-string 1 rep)) + (pcase (match-string 2 rep) + ((pred (string= "")) + (length target)) + (res (string-to-number res)))) + t t rep)) + ;; Search and replace in + ;; placeholder. Doesn't + ;; handle incremental here. + ((string-match "\\\\@/\\(.*\\)/\\(.*\\)/" rep) + (replace-match (replace-regexp-in-string + (match-string 1 rep) + (match-string 2 rep) + target t) + t t rep)) + ;; Simple replacement by placeholder. + ((string-match "\\\\@" rep) + (replace-match target t t rep)) + ;; Replacement with + ;; upcase, downcase or + ;; capitalized text. + ((string= rep "%u") #'upcase) + ((string= rep "%d") #'downcase) + ((string= rep "%c") #'capitalize) + ;; Simple replacement with + ;; whole replacement regexp. + (t rep))) + (helm-basename old) t nil subexp)) + ;; If `regexp' is not matched in `old' + ;; `replace-regexp-in-string' will + ;; return `old' unmodified. + unless (string= old new) + do (progn + (when (file-exists-p new) + (setq new (concat (file-name-sans-extension new) + (format "(%s)" count) + (file-name-extension new t)))) + (unless (string= query "!") + (setq query (helm-read-answer (format + "Replace `%s' by `%s' [!,y,n,q]" + (helm-basename old) + (helm-basename new)) + '("y" "n" "!" "q")))) + (when (string= query "q") + (cl-return (message "Operation aborted"))) + (unless (string= query "n") + (rename-file old new) + (cl-incf count))) + finally (message "%d Files renamed" count)))) + ;; This fix the emacs bug where "Emacs-Lisp:" is sent + ;; in minibuffer (not the echo area). + (sit-for 0.1) + (with-current-buffer (window-buffer (minibuffer-window)) + (delete-minibuffer-contents))) + +(defun helm-ff--prepare-str-with-regexp (str &optional rep1 rep2) + ;; This is used in `helm-ff-query-replace-on-filenames' to prepare + ;; STR when REGEXP is specified as substring e.g %:1:3 in this case + ;; substring from 1 to 3 in STR will be enclosed with parenthesis to + ;; match this substring as a subexp e.g %:1:3 on string "emacs" will + ;; be replaced by "e\\(ma\\)cs" using subexp 1 like this: + ;; (helm--replace-regexp-in-buffer-string "e\\(ma\\)cs" "fo" "emacs" nil t 1) + ;; => "efocs" + ;; ^^ + ;; Where "1" and "3" will be strings extracted with match-string + ;; from regexp and refered respectively in this function as REP1 and + ;; REP2. + (let* ((from (or (and rep1 (string-to-number rep1)) 0)) + (to (or (and rep2 (string-to-number rep2)) (length str))) + (subexp (concat "\\(" (regexp-quote (substring str from to)) "\\)")) + (before-str (unless (zerop from) + (regexp-quote (substring str 0 from)))) + (after-str (unless (= to (length str)) + (regexp-quote (substring str to (length str)))))) + (concat before-str subexp after-str))) + +;; The action. +(defun helm-ff-query-replace-fnames-on-marked (_candidate) + (let ((marked (helm-marked-candidates :with-wildcard t))) + (helm-ff-query-replace-on-filenames marked))) + +;; The command for `helm-find-files-map'. +(defun helm-ff-run-query-replace-fnames-on-marked () + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-ff-query-replace-fnames-on-marked))) +(put 'helm-ff-run-query-replace-fnames-on-marked 'helm-only t) + +(defun helm-ff-query-replace (_candidate) + (let ((bufs (cl-loop for f in (helm-marked-candidates :with-wildcard t) + collect (buffer-name (find-file-noselect f))))) + (helm-buffer-query-replace-1 nil bufs))) + +(defun helm-ff-query-replace-regexp (_candidate) + (let ((bufs (cl-loop for f in (helm-marked-candidates :with-wildcard t) + collect (buffer-name (find-file-noselect f))))) + (helm-buffer-query-replace-1 'regexp bufs))) + +(defun helm-ff-run-query-replace () + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-ff-query-replace))) +(put 'helm-ff-run-query-replace 'helm-only t) + +(defun helm-ff-run-query-replace-regexp () + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-ff-query-replace-regexp))) +(put 'helm-ff-run-query-replace-regexp 'helm-only t) + +(defun helm-ff-toggle-auto-update (_candidate) + (if helm-ff--deleting-char-backward + (progn + (message "[Auto expansion disabled]") + (sit-for 1) (message nil) + (setq helm-ff--auto-update-state nil)) + (setq helm-ff-auto-update-flag (not helm-ff-auto-update-flag)) + (setq helm-ff--auto-update-state helm-ff-auto-update-flag) + (message "[Auto expansion %s]" + (if helm-ff-auto-update-flag "enabled" "disabled")))) + +(defun helm-ff-run-toggle-auto-update () + (interactive) + (with-helm-alive-p + (helm-attrset 'toggle-auto-update '(helm-ff-toggle-auto-update . never-split)) + (helm-execute-persistent-action 'toggle-auto-update))) +(put 'helm-ff-run-toggle-auto-update 'helm-only t) + +(defun helm-ff-delete-char-backward () + "Go up one level or disable HFF auto update and delete char backward. + +Going up one level works only when pattern is a directory endings with +\"/\", otherwise this command delete char backward. + +Going up one level can be disabled if necessary by deleting \"/\" at +end of pattern using \\\\[backward-char] and \\[helm-delete-minibuffer-contents]." + (interactive) + (with-helm-alive-p + (if (and helm-ff-DEL-up-one-level-maybe + (string-match "/\\'" helm-pattern) + (file-directory-p helm-pattern)) + (call-interactively 'helm-find-files-up-one-level) + (setq helm-ff-auto-update-flag nil) + (setq helm-ff--deleting-char-backward t) + (call-interactively + (lookup-key (current-global-map) + (read-kbd-macro "DEL"))) + (helm--update-header-line)))) +(put 'helm-ff-delete-char-backward 'helm-only t) + +(defun helm-ff-delete-char-backward--exit-fn () + (setq helm-ff-auto-update-flag helm-ff--auto-update-state) + (setq helm-ff--deleting-char-backward nil)) + +(defvar helm-ff--RET-disabled nil) +(defun helm-ff-RET-1 (&optional must-match) + "Used for RET action in `helm-find-files'. +See `helm-ff-RET' for details. +If MUST-MATCH is specified exit with +`helm-confirm-and-exit-minibuffer' which handle must-match mechanism." + (let ((sel (helm-get-selection))) + (cl-assert sel nil "Trying to exit with no candidates") + (if (and (file-directory-p sel) + ;; Allows exiting with default action when a prefix arg + ;; is specified. + (null current-prefix-arg) + (null helm-ff--RET-disabled) + (not (string= "." (helm-basename sel)))) + (helm-execute-persistent-action) + (if must-match + (helm-confirm-and-exit-minibuffer) + (helm-maybe-exit-minibuffer))))) + +(defun helm-ff-RET () + "Default action for RET in `helm-find-files'. + +Behave differently depending of `helm-selection': + +- candidate basename is \".\" => open it in dired. +- candidate is a directory => expand it. +- candidate is a file => open it." + (interactive) + (helm-ff-RET-1)) +(put 'helm-ff-RET 'helm-only t) + +(defun helm-ff-TAB-1 (&optional force-menu) + "Used for TAB action in `helm-find-files'." + (let ((sel (helm-get-selection))) + (if (and (null force-menu) + (file-directory-p sel) + (not (string= "." (helm-basename sel)))) + (helm-execute-persistent-action) + (helm-select-action)))) + +(defun helm-ff-TAB (arg) + "Default action for TAB in `helm-find-files'. + +Behave differently depending of `helm-selection': + +- candidate basename is \".\" => open the action menu. +- candidate is a directory => expand it. +- candidate is a file => open action menu. + +Called with a prefix arg open menu unconditionally." + (interactive "P") + (helm-ff-TAB-1 arg)) +(put 'helm-ff-TAB 'helm-only t) + +(defun helm-ff-RET-must-match () + "Same as `helm-ff-RET' but used in must-match map." + (interactive) + (helm-ff-RET-1 t)) + +(defun helm-ff-run-grep () + "Run Grep action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-find-files-grep))) +(put 'helm-ff-run-grep 'helm-only t) + +(defun helm-ff-run-git-grep () + "Run git-grep action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-ff-git-grep))) +(put 'helm-ff-run-git-grep 'helm-only t) + +(defun helm-ff-run-grep-ag () + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-find-files-ag))) +(put 'helm-ff-run-grep-ag 'helm-only t) + +(defun helm-ff-run-pdfgrep () + "Run Pdfgrep action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-ff-pdfgrep))) +(put 'helm-ff-run-pdfgrep 'helm-only t) + +(defun helm-ff-run-zgrep () + "Run Grep action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-ff-zgrep))) +(put 'helm-ff-run-zgrep 'helm-only t) + +(defun helm-ff-run-copy-file () + "Run Copy file action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-find-files-copy))) +(put 'helm-ff-run-copy-file 'helm-only t) + +(defun helm-ff-run-rename-file () + "Run Rename file action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-find-files-rename))) +(put 'helm-ff-run-rename-file 'helm-only t) + +(defun helm-ff-run-byte-compile-file () + "Run Byte compile file action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-find-files-byte-compile))) +(put 'helm-ff-run-byte-compile-file 'helm-only t) + +(defun helm-ff-run-load-file () + "Run Load file action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-find-files-load-files))) +(put 'helm-ff-run-load-file 'helm-only t) + +(defun helm-ff-run-eshell-command-on-file () + "Run eshell command on file action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action + 'helm-find-files-eshell-command-on-file))) +(put 'helm-ff-run-eshell-command-on-file 'helm-only t) + +(defun helm-ff-run-ediff-file () + "Run Ediff file action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-find-files-ediff-files))) +(put 'helm-ff-run-ediff-file 'helm-only t) + +(defun helm-ff-run-ediff-merge-file () + "Run Ediff merge file action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action + 'helm-find-files-ediff-merge-files))) +(put 'helm-ff-run-ediff-merge-file 'helm-only t) + +(defun helm-ff-run-symlink-file () + "Run Symlink file action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-find-files-symlink))) +(put 'helm-ff-run-symlink-file 'helm-only t) + +(defun helm-ff-run-relsymlink-file () + "Run Symlink file action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-find-files-relsymlink))) +(put 'helm-ff-run-relsymlink-file 'helm-only t) + +(defun helm-ff-run-hardlink-file () + "Run Hardlink file action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-find-files-hardlink))) +(put 'helm-ff-run-hardlink-file 'helm-only t) + +(defun helm-ff-delete-files (candidate) + "Delete files default action." + (funcall helm-ff-delete-files-function candidate)) + +(defun helm-ff-run-delete-file () + "Run Delete file action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action #'helm-ff-delete-files))) +(put 'helm-ff-run-delete-file 'helm-only t) + +(defun helm-ff-run-complete-fn-at-point () + "Run complete file name action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action + 'helm-insert-file-name-completion-at-point))) +(put 'helm-ff-run-complete-fn-at-point 'helm-only t) + +(defun helm-ff-run-switch-to-eshell () + "Run switch to eshell action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-ff-switch-to-eshell))) +(put 'helm-ff-run-switch-to-eshell 'helm-only t) + +(defun helm-ff-run-switch-other-window () + "Run switch to other window action from `helm-source-find-files'. +When a prefix arg is provided, split is done vertically." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-find-files-other-window))) +(put 'helm-ff-run-switch-other-window 'helm-only t) + +(defun helm-ff-run-switch-other-frame () + "Run switch to other frame action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'find-file-other-frame))) +(put 'helm-ff-run-switch-other-frame 'helm-only t) + +(defun helm-ff-run-open-file-externally () + "Run open file externally command action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-open-file-externally))) +(put 'helm-ff-run-open-file-externally 'helm-only t) + +(defun helm-ff-run-open-file-with-default-tool () + "Run open file externally command action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-open-file-with-default-tool))) +(put 'helm-ff-run-open-file-with-default-tool 'helm-only t) + +(defun helm-ff-locate (candidate) + "Locate action function for `helm-find-files'." + (helm-locate-set-command) + (let ((default (concat (helm-basename + (expand-file-name + candidate + helm-ff-default-directory)) + (unless (or + ;; "-b" is already added when fuzzy matching. + helm-locate-fuzzy-match + ;; The locate '-b' option doesn't exists + ;; in everything (es). + (and (eq system-type 'windows-nt) + (string-match "^es" helm-locate-command))) + " -b")))) + (helm-locate-1 helm-current-prefix-arg nil 'from-ff default))) + +(defun helm-ff-run-locate () + "Run locate action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-ff-locate))) +(put 'helm-ff-run-locate 'helm-only t) + +(defun helm-files-insert-as-org-link (candidate) + (insert (format "[[%s][]]" candidate)) + (goto-char (- (point) 2))) + +(defun helm-ff-run-insert-org-link () + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-files-insert-as-org-link))) +(put 'helm-ff-run-insert-org-link 'helm-only t) + +(defun helm-ff-run-find-file-as-root () + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-find-file-as-root))) +(put 'helm-ff-run-find-file-as-root 'helm-only t) + +(defun helm-ff-run-find-alternate-file () + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'find-alternate-file))) +(put 'helm-ff-run-find-alternate-file 'helm-only t) + +(defun helm-ff-run-mail-attach-files () + "Run mail attach files command action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-ff-mail-attach-files))) +(put 'helm-ff-run-mail-attach-files 'helm-only t) + +(defun helm-ff-run-etags () + "Run Etags command action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-ff-etags-select))) +(put 'helm-ff-run-etags 'helm-only t) + +(defvar lpr-printer-switch) +(defun helm-ff-print (_candidate) + "Print marked files. + +You may to set in order +variables `lpr-command',`lpr-switches' and/or `printer-name', +but with no settings helm should detect your printer(s) and +print with the default `lpr' settings. + +NOTE: DO NOT set the \"-P\" flag in `lpr-switches', if you really +have to modify this, do it in `lpr-printer-switch'. + +Same as `dired-do-print' but for helm." + (require 'lpr) + (when (or helm-current-prefix-arg + (not helm-ff-printer-list)) + (setq helm-ff-printer-list + (helm-ff-find-printers))) + (let* ((file-list (helm-marked-candidates :with-wildcard t)) + (len (length file-list)) + (printer-name (if helm-ff-printer-list + (helm-comp-read + "Printer: " helm-ff-printer-list) + printer-name)) + (lpr-switches + (if (and (stringp printer-name) + (string< "" printer-name)) + (cons (concat lpr-printer-switch printer-name) + lpr-switches) + lpr-switches)) + (command (helm-read-string + (format "Print *%s File(s):\n%s with: " + len + (mapconcat + (lambda (f) (format "- %s\n" f)) + file-list "")) + (when (and lpr-command lpr-switches) + (mapconcat 'identity + (cons lpr-command + (if (stringp lpr-switches) + (list lpr-switches) + lpr-switches)) + " ")))) + (file-args (mapconcat (lambda (x) + (format "'%s'" x)) + file-list " ")) + (cmd-line (concat command " " file-args))) + (if command + (start-process-shell-command "helm-print" nil cmd-line) + (error "Error: Please verify your printer settings in Emacs.")))) + +(defun helm-ff-run-print-file () + "Run Print file action from `helm-source-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-ff-print))) +(put 'helm-ff-run-print-file 'helm-only t) + +(defun helm-ff-checksum (file) + "Calculate the checksum of FILE. +The checksum is copied to kill-ring. +Checksum is calculated with the md5sum, sha1sum, sha224sum, sha256sum, +sha384sum and sha512sum when available, otherwise the emacs function +`secure-hash' is used but it is slow and may crash Emacs and even the +whole system as it eats all memory." + (cl-assert (file-regular-p file) + nil "`%s' is not a regular file" file) + (let* ((algo (intern (helm-comp-read + "Algorithm: " + '(md5 sha1 sha224 sha256 sha384 sha512)))) + (cmd (concat (symbol-name algo) "sum")) + (bn (helm-basename file)) + proc) + (message "Calculating %s checksum for %s..." algo bn) + (if (executable-find cmd) + (progn + (set-process-filter + (setq proc (start-file-process cmd nil cmd "-b" file)) + (lambda (_process output) + (when output (kill-new output)))) + (set-process-sentinel + proc + `(lambda (_process event) + (when (string= event "finished\n") + (message "Calculating %s checksum for `%s' done and copied to kill-ring" + ,(symbol-name algo) ,bn))))) + (async-let ((sum (with-temp-buffer + (insert-file-contents-literally file) + (secure-hash algo (current-buffer))))) + (kill-new sum) + (message "Calculating %s checksum for `%s' done and copied to kill-ring" + algo bn))))) + +(defun helm-ff-toggle-basename (_candidate) + (with-helm-buffer + (setq helm-ff-transformer-show-only-basename + (not helm-ff-transformer-show-only-basename)) + (let* ((cand (helm-get-selection nil t)) + (target (if helm-ff-transformer-show-only-basename + (helm-basename cand) cand))) + (helm-force-update (concat (regexp-quote target) "$"))))) + +(defun helm-ff-run-toggle-basename () + (interactive) + (with-helm-alive-p + (unless (helm-empty-source-p) + (helm-ff-toggle-basename nil)))) +(put 'helm-ff-run-toggle-basename 'helm-only t) + +(defun helm-reduce-file-name-1 (fname level) + ;; This is the old version of helm-reduce-file-name, we still use it + ;; with ftp fnames as expand-file-name is not working as expected + ;; with ftp fnames (emacs bug). + (cl-loop with result + with iter = (helm-iter-reduce-fname (expand-file-name fname)) + repeat level do (setq result (helm-iter-next iter)) + finally return (or result (expand-file-name "/")))) + +(defun helm-reduce-file-name-2 (fname level) + ;; This version comes from issue #2004 (UNC paths) and should fix + ;; it. It works with local files and remote files as well but not + ;; with ftp, see helm-reduce-file-name-1. + (while (> level 0) + (unless (or (string= fname "/") + (string= (file-remote-p fname 'localname) "/")) + (setq fname (expand-file-name + (concat (expand-file-name fname) "/../")))) + (setq level (1- level))) + fname) + +(defun helm-reduce-file-name (fname level) + "Reduce FNAME by number LEVEL from end." + (if (helm-aand (file-remote-p fname 'method) + (string= it "ftp")) + (helm-reduce-file-name-1 fname level) + (helm-reduce-file-name-2 fname level))) + +(defun helm-iter-reduce-fname (fname) + "Yield FNAME reduced by one level at each call." + (let ((split (split-string fname "/" t))) + (unless (or (null split) + (string-match "\\`\\(~\\|[[:alpha:]]:\\)" (car split))) + (setq split (cons "/" split))) + (lambda () + (when (and split (cdr split)) + (cl-loop for i in (setq split (butlast split)) + concat (if (string= i "/") i (concat i "/"))))))) + +(defvar helm-find-files--level-tree nil) +(defvar helm-find-files--level-tree-iterator nil) +(defun helm-find-files-up-one-level (arg) + "Go up one level like unix command `cd ..'. +If prefix numeric arg is given go ARG level up." + (interactive "p") + (with-helm-alive-p + (let ((src (helm-get-current-source))) + (when (and (helm-file-completion-source-p src) + (not (helm-ff--invalid-tramp-name-p))) + (with-helm-window + (when (helm-follow-mode-p) + (helm-follow-mode -1) (message nil))) + ;; When going up one level we want to be at the line + ;; corresponding to actual directory, so store this info + ;; in `helm-ff-last-expanded'. + (let ((cur-cand (helm-get-selection nil nil src)) + (new-pattern (helm-reduce-file-name helm-pattern arg))) + ;; Ensure visibility on all candidates for preselection. + (helm-attrset 'candidate-number-limit + (if helm-ff-up-one-level-preselect + (max (gethash new-pattern + helm-ff--directory-files-hash + helm-ff-candidate-number-limit) + helm-ff-candidate-number-limit) + helm-ff-candidate-number-limit)) + (cond ((file-directory-p helm-pattern) + (setq helm-ff-last-expanded helm-ff-default-directory)) + ((file-exists-p helm-pattern) + (setq helm-ff-last-expanded helm-pattern)) + ((and cur-cand (file-exists-p cur-cand)) + (setq helm-ff-last-expanded cur-cand))) + (unless helm-find-files--level-tree + (setq helm-find-files--level-tree + (cons helm-ff-default-directory + helm-find-files--level-tree))) + (setq helm-find-files--level-tree-iterator nil) + (push new-pattern helm-find-files--level-tree) + (helm-set-pattern new-pattern helm-suspend-update-flag) + (with-helm-after-update-hook (helm-ff-retrieve-last-expanded))))))) +(put 'helm-find-files-up-one-level 'helm-only t) + +(defun helm-find-files-down-last-level () + "Retrieve previous paths reached by `C-l' in helm-find-files." + (interactive) + (with-helm-alive-p + (when (and (helm-file-completion-source-p) + (not (helm-ff--invalid-tramp-name-p))) + (unless helm-find-files--level-tree-iterator + (setq helm-find-files--level-tree-iterator + (helm-iter-list (cdr helm-find-files--level-tree)))) + (setq helm-find-files--level-tree nil) + (helm-aif (helm-iter-next helm-find-files--level-tree-iterator) + (helm-set-pattern it) + (setq helm-find-files--level-tree-iterator nil))))) +(put 'helm-find-files-down-last-level 'helm-only t) + +(defun helm-find-files--reset-level-tree () + (setq helm-find-files--level-tree-iterator nil + helm-find-files--level-tree nil)) + +(add-hook 'helm-cleanup-hook 'helm-find-files--reset-level-tree) +(add-hook 'post-self-insert-hook 'helm-find-files--reset-level-tree) +(add-hook 'helm-after-persistent-action-hook 'helm-find-files--reset-level-tree) + +(defun helm-ff-retrieve-last-expanded () + "Move overlay to last visited directory `helm-ff-last-expanded'. +This happen after using `helm-find-files-up-one-level', +or hitting C-j on \"..\"." + (when helm-ff-last-expanded + (let ((presel (if helm-ff-transformer-show-only-basename + (helm-basename + (directory-file-name helm-ff-last-expanded)) + (directory-file-name helm-ff-last-expanded)))) + (with-helm-window + (when (re-search-forward (concat "^" (regexp-quote presel) "$") nil t) + (forward-line 0) + (helm-mark-current-line))) + (setq helm-ff-last-expanded nil)))) + +(defun helm-ff-move-to-first-real-candidate () + "When candidate is an incomplete file name move to first real candidate." + (let* ((src (helm-get-current-source)) + (name (assoc-default 'name src)) + ;; Ensure `helm-file-completion-source-p' returns nil on + ;; `helm-read-file-name' history. + minibuffer-completing-file-name) + (helm-aif (and (helm-file-completion-source-p src) + (not (helm-empty-source-p)) + ;; Prevent dired commands moving to first real + ;; (Issue #910). + (or (memq (intern-soft name) + helm-ff-goto-first-real-dired-exceptions) + (not (string-match "\\`[Dd]ired-" name))) + helm-ff--move-to-first-real-candidate + (helm-get-selection nil nil src)) + (unless (or (not (stringp it)) + (and (string-match helm-tramp-file-name-regexp it) + (not (file-remote-p it nil t))) + (file-exists-p it)) + (helm-next-line))))) + +;;; Auto-update - helm-find-files auto expansion of directories. +;; +;; +(defun helm-ff-update-when-only-one-matched () + "Expand to directory when sole completion. +When only one candidate is remaining and it is a directory, +expand to this directory. +This happen only when `helm-ff-auto-update-flag' is non--nil +or when `helm-pattern' is equal to \"~/\"." + (let ((src (helm-get-current-source))) + (when (and (helm-file-completion-source-p src) + (not (get-buffer-window helm-action-buffer 'visible)) + (not (helm-ff--invalid-tramp-name-p)) + (not (string-match-p "\\`[.]\\{2\\}[^/]+" + (helm-basename helm-pattern)))) + (with-helm-buffer + (let* ((history-p (string= (assoc-default 'name src) + "Read File Name History")) + (pat (if (string-match helm-tramp-file-name-regexp + helm-pattern) + (helm-ff--create-tramp-name helm-pattern) + helm-pattern)) + (completed-p (string= (file-name-as-directory + (expand-file-name + (substitute-in-file-name pat))) + helm-ff-default-directory)) + (candnum (helm-get-candidate-number)) + (lt2-p (and (<= candnum 2) + (>= (string-width (helm-basename helm-pattern)) 2))) + (cur-cand (prog2 + (unless (or completed-p + (file-exists-p pat) + history-p (null lt2-p)) + ;; Only one non--existing candidate + ;; and one directory candidate, move to it, + ;; but not when renaming, copying etc..., + ;; so for this use + ;; `helm-ff-move-to-first-real-candidate' + ;; instead of `helm-next-line' (Issue #910). + (helm-ff-move-to-first-real-candidate)) + (helm-get-selection nil nil src)))) + (when (and (or (and helm-ff-auto-update-flag + (null helm-ff--deleting-char-backward) + ;; Issue #295 + ;; File predicates are returning t + ;; with paths like //home/foo. + ;; So check it is not the case by regexp + ;; to allow user to do C-a / to start e.g + ;; entering a tramp method e.g /sudo::. + (not (string-match "\\`//" helm-pattern)) + (not (eq last-command 'helm-yank-text-at-point))) + ;; Fix issue #542. + (string= helm-pattern "~/") + ;; Only one remaining directory, expand it. + (and (= candnum 1) + helm-ff--auto-update-state + (file-accessible-directory-p pat) + (null helm-ff--deleting-char-backward))) + (or + ;; Only one candidate remaining + ;; and at least 2 char in basename. + lt2-p + ;; Already completed. + completed-p) + (not history-p) ; Don't try to auto complete in history. + (stringp cur-cand) + (file-accessible-directory-p cur-cand)) + (if (and (not (helm-dir-is-dot cur-cand)) ; [1] + ;; Maybe we are here because completed-p is true + ;; but check this again to be sure. (Windows fix) + (<= candnum 2)) ; [2] + ;; If after going to next line the candidate + ;; is not one of "." or ".." [1] + ;; and only one candidate is remaining [2], + ;; assume candidate is a new directory to expand, and do it. + (helm-set-pattern (file-name-as-directory cur-cand)) + ;; The candidate is one of "." or ".." + ;; that mean we have entered the last letter of the directory name + ;; in prompt, so expansion is already done, just add the "/" at end + ;; of name unless helm-pattern ends with "." + ;; (i.e we are writing something starting with ".") + (unless (string-match "\\`.*[.]\\{1\\}\\'" helm-pattern) + (helm-set-pattern + ;; Need to expand-file-name to avoid e.g /ssh:host:./ in prompt. + (expand-file-name (file-name-as-directory helm-pattern))))) + (helm-check-minibuffer-input))))))) + +(defun helm-ff-auto-expand-to-home-or-root () + "Allow expanding to home/user directory or root or text yanked after pattern." + (when (and (helm-file-completion-source-p) + (with-current-buffer (window-buffer (minibuffer-window)) (eolp)) + (not (string-match helm-ff-url-regexp helm-pattern))) + (cond ((and (not (file-remote-p helm-pattern)) + (null (file-exists-p helm-pattern)) + (string-match-p + "\\`\\([.]\\|\\s-\\)\\{2\\}[^/]+" + (helm-basename helm-pattern)) + (string-match-p "/\\'" helm-pattern)) + (helm-ff-recursive-dirs helm-pattern) + (with-helm-window (helm-check-minibuffer-input))) + ((string-match + "\\(?:\\`~/\\)\\|/?\\$.*/\\|/\\./\\|/\\.\\./\\|/~.*/\\|//\\|\\(/[[:alpha:]]:/\\|\\s\\+\\)" + helm-pattern) + (let* ((match (match-string 0 helm-pattern)) + (input (cond ((string= match "/./") + (expand-file-name default-directory)) + ((string= helm-pattern "/../") "/") + ((string-match-p "\\`/\\$" match) + (let ((sub (substitute-in-file-name match))) + (if (file-directory-p sub) + sub (replace-regexp-in-string "/\\'" "" sub)))) + (t (helm-ff--expand-substitued-pattern helm-pattern))))) + ;; `file-directory-p' returns t on "/home/me/." (issue #1844). + (if (and (file-directory-p input) + (not (string-match-p "[^.]\\.\\'" input))) + (setq helm-ff-default-directory + (setq input (file-name-as-directory input))) + (setq helm-ff-default-directory (file-name-as-directory + (file-name-directory input)))) + (with-helm-window + (helm-set-pattern input) + (helm-check-minibuffer-input))))))) + +(defun helm-ff--expand-file-name-no-dot (name &optional directory) + "Prevent expanding \"/home/user/.\" to \"/home/user\"." + ;; Issue #1844 - If user enter "~/." to type an hidden filename + ;; don't expand to /home/him e.g. + ;; (expand-file-name "~/.") =>"/home/thierry" + ;; (helm-ff--expand-substitued-pattern "~/.") =>"/home/thierry/." + (concat (expand-file-name name directory) + (and (string-match "[^.]\\.\\'" name) "/."))) + +(defun helm-ff--expand-substitued-pattern (pattern) + ;; [Windows] On UNC paths "/" expand to current machine, + ;; so use the root of current Drive. (i.e "C:/") + (let* ((directory (and (memq system-type '(windows-nt ms-dos)) + (getenv "SystemDrive"))) + ;; On Windows use a simple call to `expand-file-name' to + ;; avoid Issue #2004. + (expand-fn (if directory + #'expand-file-name + #'helm-ff--expand-file-name-no-dot))) + (funcall expand-fn (helm-substitute-in-filename pattern) + ;; directory is nil on Nix. + directory))) + +(defun helm-substitute-in-filename (fname) + "Substitute all parts of FNAME from start up to \"~/\" or \"/\". +On windows system substitute from start up to \"/[[:lower:]]:/\". +This function is needed for `helm-ff-auto-expand-to-home-or-root' +and should be used carefully elsewhere, or not at all, using +`substitute-in-file-name' instead." + (cond ((and helm--url-regexp + (string-match-p helm--url-regexp fname)) + fname) + ((and (file-remote-p fname) + helm-substitute-in-filename-stay-on-remote) + (let ((sub (substitute-in-file-name fname))) + (if (file-directory-p sub) + sub (replace-regexp-in-string "/\\'" "" sub)))) + (t + (with-temp-buffer + (insert fname) + (goto-char (point-min)) + (when (memq system-type '(windows-nt ms-dos)) + (skip-chars-forward "/")) ;; Avoid infloop in UNC paths Issue #424 + (if (re-search-forward "~.*/?\\|//\\|/[[:alpha:]]:/" nil t) + (let ((match (match-string 0))) + (goto-char (if (or (string= match "//") + (string-match-p "/[[:alpha:]]:/" match)) + (1+ (match-beginning 0)) + (match-beginning 0))) + (buffer-substring-no-properties (point) (point-at-eol))) + fname))))) + +(defun helm-point-file-in-dired (file) + "Put point on filename FILE in dired buffer." + (unless (and helm--url-regexp + (string-match-p helm--url-regexp file)) + (let ((target (expand-file-name (helm-substitute-in-filename file)))) + (dired (file-name-directory target)) + (dired-goto-file target)))) + +(defun helm-marked-files-in-dired (_candidate) + "Open a dired buffer with only marked files. + +With a prefix arg toggle dired buffer to wdired mode." + (advice-add 'wdired-finish-edit :override #'helm--advice-wdired-finish-edit) + (advice-add 'wdired-get-filename :override #'helm--advice-wdired-get-filename) + (let* ((marked (helm-marked-candidates :with-wildcard t)) + (current (car marked))) + (unless (and helm--url-regexp + (string-match-p helm--url-regexp current)) + (let ((target (expand-file-name (helm-substitute-in-filename current)))) + (dired (cons helm-ff-default-directory marked)) + (dired-goto-file target) + (when (or helm-current-prefix-arg current-prefix-arg) + (call-interactively 'wdired-change-to-wdired-mode)))))) + +(defun helm-ff-run-marked-files-in-dired () + "Execute `helm-marked-files-in-dired' interactively." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-marked-files-in-dired))) +(put 'helm-ff-run-marked-files-in-dired 'helm-only t) + +(defun helm-ff--create-tramp-name (fname) + "Build filename from `helm-pattern' like /su:: or /sudo::." + ;; `tramp-make-tramp-file-name' takes 7 args on emacs-26 whereas it + ;; takes only 5 args in emacs-24/25. + (apply #'tramp-make-tramp-file-name + ;; `tramp-dissect-file-name' returns a list in emacs-26 + ;; whereas in 24.5 it returns a vector, thus the car is a + ;; symbol (`tramp-file-name') which is not needed as argument + ;; for `tramp-make-tramp-file-name' so transform the cdr in + ;; vector, and for 24.5 use directly the returned value. + (cl-loop with v = (helm-ff--tramp-cons-or-vector + (tramp-dissect-file-name fname)) + for i across v collect i))) + +(defun helm-ff--tramp-cons-or-vector (vector-or-cons) + "Return VECTOR-OR-CONS as a vector." + (pcase vector-or-cons + (`(,_l . ,ll) (vconcat ll)) + ((and vec (pred vectorp)) vec))) + +(defun helm-ff--get-tramp-methods () + "Returns a list of the car of `tramp-methods'." + (or helm-ff--tramp-methods + (setq helm-ff--tramp-methods (mapcar 'car tramp-methods)))) + +(defun helm-ff--previous-mh-tramp-method (str) + (save-match-data + (with-temp-buffer + (insert str) + (when (re-search-backward + (concat "\\([|]\\)\\(" + (mapconcat 'identity (helm-ff--get-tramp-methods) "\\|") + "\\):") + nil t) + (list + (buffer-substring-no-properties (point-at-bol) (match-beginning 2)) + (buffer-substring-no-properties (match-beginning 2) (match-end 2))))))) + +(defun helm-ff--get-host-from-tramp-invalid-fname (fname) + "Extract hostname from an incomplete tramp file name. +Return nil on valid file name remote or not." + ;; Check first if whole file is remote (file-remote-p is inefficient + ;; in this case) otherwise we are matching e.g. /home/you/ssh:foo/ + ;; which is not a remote name. + ;; FIXME this will not work with a directory or a file named like + ;; "ssh:foo" and located at root (/) but it seems there is no real + ;; solution apart disabling tramp-mode when a file/dir located at / + ;; is matching helm-tramp-file-name-regexp; This would prevent usage + ;; of tramp if one have such a directory at / (who would want to + ;; have such a dir at / ???) See emacs-bug#31489. + (when (string-match-p helm-tramp-file-name-regexp fname) + (let* ((bn (helm-basename fname)) + (bd (replace-regexp-in-string (regexp-quote bn) "" fname)) + (split (split-string bn ":" t)) + (meth (car (member (car split) + (helm-ff--get-tramp-methods))))) + (and meth (string= bd "/") (car (last split)))))) + +(cl-defun helm-ff--tramp-hostnames (&optional (pattern helm-pattern)) + "Get a list of hosts for tramp method found in `helm-pattern'. +Argument PATTERN default to `helm-pattern', it is here only for debugging +purpose." + (when (string-match helm-tramp-file-name-regexp pattern) + (let* ((mh-method (helm-ff--previous-mh-tramp-method pattern)) + (method (or (cadr mh-method) (match-string 1 pattern))) + (current-mh-host (helm-aif (and mh-method + (helm-ff--get-host-from-tramp-invalid-fname pattern)) + (concat (car mh-method) method ":" + (car (split-string it "|" t))))) + (all-methods (helm-ff--get-tramp-methods)) + (comps (cl-loop for (f . h) in (tramp-get-completion-function method) + append (cl-loop for e in (funcall f (car h)) + for host = (and (consp e) (cadr e)) + when (and host (not (member host all-methods))) + collect (concat (or (car mh-method) "/") + method ":" host))))) + (helm-fast-remove-dups + (delq nil (cons current-mh-host comps)) + :test 'equal)))) + +(defun helm-ff-before-action-hook-fn () + "Exit helm when user try to execute action on an invalid tramp fname." + (let* ((src (helm-get-current-source)) + (cand (helm-get-selection nil nil src))) + (when (and (helm-file-completion-source-p src) + (stringp cand) + (helm-ff--invalid-tramp-name-p cand) ; Check candidate. + (helm-ff--invalid-tramp-name-p)) ; check helm-pattern. + (error "Error: Unknown file or directory `%s'" cand)))) +(add-hook 'helm-before-action-hook 'helm-ff-before-action-hook-fn) + +(cl-defun helm-ff--invalid-tramp-name-p (&optional (pattern helm-pattern)) + "Return non--nil when PATTERN is an invalid tramp filename." + (string= (helm-ff-set-pattern pattern) + "Invalid tramp file name")) + +(defun helm-ff--tramp-postfixed-p (str) + (let (result) + (save-match-data + (with-temp-buffer + (save-excursion (insert str)) + (helm-awhile (search-forward ":" nil t) + (if (save-excursion + (forward-char -1) + (looking-back + (mapconcat 'identity (helm-ff--get-tramp-methods) "\\|") + (point-at-bol))) + (setq result nil) + (setq result it))))) + result)) + +(defun helm-ff-set-pattern (pattern) + "Handle tramp filenames in `helm-pattern'." + (let* ((methods (helm-ff--get-tramp-methods)) + ;; Returns the position of last ":" entered. + (postfixed (helm-ff--tramp-postfixed-p pattern)) + (reg "\\`/\\([^[/:]+\\|[^/]+]\\):.*:") + cur-method tramp-name) + ;; In some rare cases tramp can return a nil input, + ;; so be sure pattern is a string for safety (Issue #476). + (unless pattern (setq pattern "")) + (cond ((string-match helm-ff-url-regexp pattern) pattern) + ((string-match "\\`\\$" pattern) + (substitute-in-file-name pattern)) + ((string= pattern "") "") + ((string-match "\\`[.]\\{1,2\\}/\\'" pattern) + (expand-file-name pattern)) + ;; Directories ending by a dot (issue #1940) + ((string-match "[^/][.]/\\'" pattern) + (expand-file-name pattern)) + ((string-match ".*\\(~?/?[.]\\{1\\}/\\)\\'" pattern) + (expand-file-name default-directory)) + ((string-match ".*\\(~//\\|//\\)\\'" pattern) + (expand-file-name "/")) ; Expand to "/" or "c:/" + ((string-match "\\`\\(~/\\|.*/~/\\)\\'" pattern) + (expand-file-name "~/")) + ((string-match "\\`~/" pattern) + (expand-file-name pattern)) + ;; Match "/method:maybe_hostname:~" + ((and (string-match (concat reg "~") pattern) + postfixed + (setq cur-method (match-string 1 pattern)) + (member cur-method methods)) + (setq tramp-name (expand-file-name + (helm-ff--create-tramp-name + (match-string 0 pattern)))) + (replace-match tramp-name nil t pattern)) + ;; Match "/method:maybe_hostname:" + ((and (string-match reg pattern) + postfixed + (setq cur-method (match-string 1 pattern)) + (member cur-method methods)) + (setq tramp-name (helm-ff--create-tramp-name + (match-string 0 pattern))) + (replace-match tramp-name nil t pattern)) + ;; Match "/hostname:" + ((and (string-match helm-tramp-file-name-regexp pattern) + postfixed + (setq cur-method (match-string 1 pattern)) + (and cur-method (not (member cur-method methods)))) + (setq tramp-name (helm-ff--create-tramp-name + (match-string 0 pattern))) + (replace-match tramp-name nil t pattern)) + ;; Match "/method:" in this case don't try to connect. + ((and (null postfixed) + (string-match helm-tramp-file-name-regexp pattern) + (member (match-string 1 pattern) methods)) + "Invalid tramp file name") ; Write in helm-buffer. + ;; Return PATTERN unchanged. + (t pattern)))) + +(defun helm-find-files-get-candidates (&optional require-match) + "Create candidate list for `helm-source-find-files'." + (let* ((path (helm-ff-set-pattern helm-pattern)) + (dir-p (file-accessible-directory-p path)) + basedir + invalid-basedir + non-essential + (tramp-verbose helm-tramp-verbose)) ; No tramp message when 0. + ;; Tramp check if path is valid without waiting a valid + ;; connection and may send a file-error. + (setq helm--ignore-errors (file-remote-p path)) + (set-text-properties 0 (length path) nil path) + ;; Issue #118 allow creation of newdir+newfile. + (unless (or + ;; A tramp file name not completed. + (string= path "Invalid tramp file name") + ;; An empty pattern + (string= path "") + (and (string-match-p ":\\'" path) + (helm-ff--tramp-postfixed-p path)) + ;; Check if base directory of PATH is valid. + (helm-aif (file-name-directory path) + ;; If PATH is a valid directory IT=PATH, + ;; else IT=basedir of PATH. + (file-directory-p it))) + ;; BASEDIR is invalid, that's mean user is starting + ;; to write a non--existing path in minibuffer + ;; probably to create a 'new_dir' or a 'new_dir+new_file'. + (setq invalid-basedir t)) + ;; Don't set now `helm-pattern' if `path' == "Invalid tramp file name" + ;; like that the actual value (e.g /ssh:) is passed to + ;; `helm-ff--tramp-hostnames'. + (unless (or (string= path "Invalid tramp file name") + invalid-basedir) ; Leave helm-pattern unchanged. + (setq helm-ff-auto-update-flag ; [1] + ;; Unless auto update is disabled start auto updating only + ;; at third char. + (unless (or (null helm-ff--auto-update-state) + ;; But don't enable auto update when + ;; deleting backward. + helm-ff--deleting-char-backward + (and dir-p (not (string-match-p "/\\'" path)))) + (or (>= (length (helm-basename path)) 3) dir-p))) + ;; At this point the tramp connection is triggered. + (helm-log + "Pattern=%S" + (setq helm-pattern (helm-ff--transform-pattern-for-completion path))) + ;; This have to be set after [1] to allow deleting char backward. + (setq basedir (or (helm-aand + (if (and dir-p helm-ff-auto-update-flag) + ;; Add the final "/" to path + ;; when `helm-ff-auto-update-flag' is enabled. + (file-name-as-directory path) + (if (string= path "") + "/" (file-name-directory path))) + (expand-file-name it)) + default-directory)) + (setq helm-ff-default-directory + (if (string= helm-pattern "") + (expand-file-name "/") ; Expand to "/" or "c:/" + ;; If path is an url *default-directory have to be nil. + (unless (or (string-match helm-ff-url-regexp path) + (and helm--url-regexp + (string-match helm--url-regexp path))) + basedir)))) + (when (and (string-match ":\\'" path) + (file-remote-p basedir nil t)) + (setq helm-pattern basedir)) + (cond ((string= path "Invalid tramp file name") + (or (helm-ff--tramp-hostnames) ; Hostnames completion. + (prog2 + ;; `helm-pattern' have not been modified yet. + ;; Set it here to the value of `path' that should be now + ;; "Invalid tramp file name" and set the candidates list + ;; to ("Invalid tramp file name") to make `helm-pattern' + ;; match single candidate "Invalid tramp file name". + (setq helm-pattern path) + ;; "Invalid tramp file name" is now printed + ;; in `helm-buffer'. + (list path)))) + ((or (and (file-regular-p path) + (eq last-repeatable-command 'helm-execute-persistent-action)) + ;; `ffap-url-regexp' don't match until url is complete. + (string-match helm-ff-url-regexp path) + invalid-basedir + (and (not (file-exists-p path)) (string-match "/$" path)) + (and helm--url-regexp (string-match helm--url-regexp path))) + (list path)) + ((string= path "") (helm-ff-directory-files "/")) + ;; Check here if directory is accessible (not working on Windows). + ((and (file-directory-p path) (not (file-readable-p path))) + (list (format "file-error: Opening directory permission denied `%s'" path))) + ;; A fast expansion of PATH is made only if `helm-ff-auto-update-flag' + ;; is enabled. + ((and dir-p helm-ff-auto-update-flag) + (helm-ff-directory-files path)) + (t (append (unless (or require-match + ;; Check here if path is an existing + ;; file before adding it to + ;; candidates, it was previously done + ;; in the sort function but this + ;; create a bug with remote files + ;; when path is at the same time a + ;; pattern matching a candidate and a + ;; real candidate e.g. ack and + ;; ack-grep in /usr/bin. This is due + ;; presumably to a latency more + ;; important with remote files which + ;; lead to a confusion with the + ;; pattern matching one candidate and + ;; the real candidate which is same + ;; as pattern. + (file-exists-p path) + ;; When `helm-ff-auto-update-flag' has been + ;; disabled, whe don't want PATH to be added on top + ;; if it is a directory. + dir-p) + (list path)) + (helm-ff-directory-files basedir)))))) + +(defun helm-list-directory (directory) + "List directory DIRECTORY. + +If DIRECTORY is remote use `helm-list-directory-function' otherwise use +`directory-files'." + (let* ((remote (file-remote-p directory 'method)) + (helm-list-directory-function + (if (and remote (not (string= remote "ftp"))) + helm-list-directory-function + #'helm-list-dir-lisp)) + (remote-fn-p (eq helm-list-directory-function + 'helm-list-dir-external)) + (sort-method (cl-case helm-ff-initial-sort-method + (newest (if (and remote remote-fn-p) + "-t" #'file-newer-than-file-p)) + (size (if (and remote remote-fn-p) + "-S" #'helm-ff-file-larger-that-file-p)) + (t nil)))) + (if remote + (funcall helm-list-directory-function directory sort-method) + (if sort-method + (sort (directory-files directory t directory-files-no-dot-files-regexp) + sort-method) + (directory-files directory t directory-files-no-dot-files-regexp))))) + +(defsubst helm-ff-file-larger-that-file-p (f1 f2) + (let ((attr1 (file-attributes f1)) + (attr2 (file-attributes f2))) + (> (nth 7 attr1) (nth 7 attr2)))) + +(defun helm-list-dir-lisp (directory &optional sort-method) + "List DIRECTORY with `file-name-all-completions' as backend. + +Add a `helm-ff-dir' property on each fname ending with \"/\"." + ;; NOTE: `file-name-all-completions' and `directory-files' and most + ;; tramp file handlers don't handle cntrl characters in fnames, so + ;; the displayed files will be plain wrong in this case, even worst + ;; the filenames will be splitted in two or more filenames. + (cl-loop for f in (sort (file-name-all-completions "" directory) + (or sort-method 'string-lessp)) + unless (or (string= f "") + (member f '("./" "../")) + ;; Ignore the tramp names from / + ;; completion, e.g. ssh: scp: etc... + (char-equal (aref f (1- (length f))) ?:)) + if (and (helm--dir-name-p f) + (helm--dir-file-name f directory)) + collect (propertize it 'helm-ff-dir t) + else collect (propertize (expand-file-name f directory) + 'helm-ff-file t))) + +(defun helm-list-dir-external (dir &optional sort-method) + "List directory DIR with external shell command as backend. + +This function is fast enough to be used for remote files and save the +type of files at the same time in a property for using it later in the +transformer." + (let ((default-directory (file-name-as-directory + (expand-file-name dir)))) + (with-temp-buffer + (when (eq (process-file-shell-command + (format + ;; -A remove dot files, -F append [*=@|/>] at eof + ;; and -Q quote the real filename. If not using -Q, + ;; there is no way to distinguish if foo* is a real + ;; file or if it is foo the executable file so with + ;; -Q we have "foo"* for the executable file foo and + ;; "foo*" for the real file foo. The downside is + ;; that we need an extra step to remove the quotes + ;; at the end which impact performances. + "ls -A -1 -F -b -Q %s | awk -v dir=%s '{print dir $0}'" + (or sort-method "") + (shell-quote-argument default-directory)) + nil t nil) + 0) + (goto-char (point-min)) + (save-excursion + (while (re-search-forward "[*=@|/>]$" nil t) + ;; A line looks like /home/you/"foo"@ + (helm-acase (match-string 0) + ("*" (replace-match "") + (put-text-property + (point-at-bol) (point-at-eol) 'helm-ff-exe t)) + ("@" (replace-match "") + (put-text-property + (point-at-bol) (point-at-eol) 'helm-ff-sym t)) + ("/" (replace-match "") + (put-text-property + (point-at-bol) (point-at-eol) 'helm-ff-dir t)) + (("=" "|" ">") (replace-match ""))))) + (while (re-search-forward "[\"]" nil t) + (replace-match "")) + (add-text-properties (point-min) (point-max) '(helm-ff-file t)) + (split-string (buffer-string) "\n" t))))) + +(defun helm-ff-directory-files (directory) + "List contents of DIRECTORY. +Argument FULL mean absolute path. +It is same as `directory-files' but always returns the +dotted filename '.' and '..' even on root directories in Windows +systems." + (setq directory (file-name-as-directory + (expand-file-name directory))) + (let* (file-error + (ls (condition-case err + (helm-list-directory directory) + ;; Handle file-error from here for Windows + ;; because predicates like `file-readable-p' and friends + ;; seem broken on emacs for Windows systems (always returns t). + ;; This should never be called on GNU/Linux/Unix + ;; as the error is properly intercepted in + ;; `helm-find-files-get-candidates' by `file-readable-p'. + (file-error + (prog1 + (list (format "%s:%s" + (car err) + (mapconcat 'identity (cdr err) " "))) + (setq file-error t))))) + (dot (concat directory ".")) + (dot2 (concat directory ".."))) + (puthash directory (+ (length ls) 2) helm-ff--directory-files-hash) + (append (and (not file-error) (list dot dot2)) ls))) + +(defun helm-ff-handle-backslash (fname) + ;; Allow creation of filenames containing a backslash. + (cl-loop with bad = '((92 . "")) + for i across fname + if (assq i bad) concat (cdr it) + else concat (string i))) + +(defun helm-ff-fuzzy-matching-p () + (and helm-ff-fuzzy-matching + (not (memq helm-mm-matching-method '(multi1 multi3p))))) + +(defun helm-ff--transform-pattern-for-completion (pattern) + "Maybe return PATTERN with it's basename modified as a regexp. +This happen only when `helm-ff-fuzzy-matching' is enabled. +This provide a similar behavior as `ido-enable-flex-matching'. +See also `helm--mapconcat-pattern'. +If PATTERN is an url returns it unmodified. +When PATTERN contain a space fallback to multi-match. +If basename contain one or more space fallback to multi-match. +If PATTERN is a valid directory name,return PATTERN unchanged." + ;; handle bad filenames containing a backslash (no more needed in + ;; emacs-26, also prevent regexp matching with e.g. "\|"). + ;; (setq pattern (helm-ff-handle-backslash pattern)) + (let ((bn (helm-basename pattern)) + (bd (or (helm-basedir pattern) "")) + ;; Trigger tramp connection with file-directory-p. + (dir-p (file-directory-p pattern)) + (tramp-p (cl-loop for (m . f) in tramp-methods + thereis (string-match m pattern)))) + ;; Always regexp-quote base directory name to handle + ;; crap dirnames such e.g bookmark+ + (cond + ((or (and dir-p tramp-p (string-match ":\\'" pattern)) + (string= pattern "") + (and dir-p (<= (length bn) 2)) + ;; Fix Issue #541 when BD have a subdir similar + ;; to BN, don't switch to match plugin + ;; which will match both. + (and dir-p (string-match (regexp-quote bn) bd))) + ;; Use full PATTERN on e.g "/ssh:host:". + (regexp-quote pattern)) + ;; Prefixing BN with a space call multi-match completion. + ;; This allow showing all files/dirs matching BN (Issue #518). + ;; FIXME: some multi-match methods may not work here. + (dir-p (concat (regexp-quote bd) " " (regexp-quote bn))) + ((or (not (helm-ff-fuzzy-matching-p)) + (string-match "\\s-" bn)) ; Fall back to multi-match. + (concat (regexp-quote bd) bn)) + ((or (string-match "[*][.]?.*" bn) ; Allow entering wilcard. + (string-match "/$" pattern) ; Allow mkdir. + (string-match helm-ff-url-regexp pattern) + (and (string= helm-ff-default-directory "/") tramp-p)) + ;; Don't treat wildcards ("*") as regexp char. + ;; (e.g ./foo/*.el => ./foo/[*].el) + (concat (regexp-quote bd) + (replace-regexp-in-string "[*]" "[*]" bn))) + (t (concat (regexp-quote bd) + (if (>= (length bn) 2) ; wait 2nd char before concating. + (helm--mapconcat-pattern bn) + (concat ".*" (regexp-quote bn)))))))) + +(defun helm-dir-is-dot (dir) + (string-match "\\(?:/\\|\\`\\)\\.\\{1,2\\}\\'" dir)) + +(defun helm-ff-save-history () + "Store the last value of `helm-ff-default-directory' in `helm-ff-history'. +Note that only existing directories are saved here." + (when (and helm-ff-default-directory + (helm-file-completion-source-p) + (file-directory-p helm-ff-default-directory)) + (set-text-properties 0 (length helm-ff-default-directory) + nil helm-ff-default-directory) + (push helm-ff-default-directory helm-ff-history))) +(add-hook 'helm-cleanup-hook 'helm-ff-save-history) + +(defun helm-files-save-file-name-history (&optional force) + "Save marked files to `file-name-history'." + (let* ((src (helm-get-current-source)) + (src-name (assoc-default 'name src))) + (when (or force (helm-file-completion-source-p src) + (member src-name helm-files-save-history-extra-sources)) + (let ((mkd (helm-marked-candidates :with-wildcard t)) + (history-delete-duplicates t)) + (cl-loop for sel in mkd + when (and sel + (stringp sel) + (file-exists-p sel) + (not (file-directory-p sel))) + do + ;; we use `abbreviate-file-name' here because + ;; other parts of Emacs seems to, + ;; and we don't want to introduce duplicates. + (add-to-history 'file-name-history + (abbreviate-file-name sel))))))) +(add-hook 'helm-exit-minibuffer-hook 'helm-files-save-file-name-history) + +(defun helm-ff-valid-symlink-p (file) + (helm-aif (condition-case-unless-debug nil + ;; `file-truename' send error + ;; on cyclic symlinks (Issue #692). + (file-truename file) + (error nil)) + (file-exists-p it))) + +(defun helm-get-default-mode-for-file (filename) + "Return the default mode to open FILENAME." + (let ((mode (cl-loop for (r . m) in auto-mode-alist + thereis (and (string-match r filename) m)))) + (or (and (symbolp mode) mode) "Fundamental"))) + +(defun helm-ff-properties (candidate) + "Show file properties of CANDIDATE in a tooltip or message." + (require 'helm-external) ; For `helm-get-default-program-for-file'. + (helm-aif (helm-file-attributes candidate) + (let* ((dired-line (helm-file-attributes + candidate :dired t :human-size t)) + (type (cl-getf it :type)) + (mode-type (cl-getf it :mode-type)) + (owner (cl-getf it :uid)) + (owner-right (cl-getf it :user t)) + (group (cl-getf it :gid)) + (group-right (cl-getf it :group)) + (other-right (cl-getf it :other)) + (trash (and (helm-ff-trash-file-p candidate) + (helm-ff--get-dest-file-from-trash + (helm-ff-trash-list) + (replace-regexp-in-string + "\\.trashinfo\\'" "" candidate)))) + (size (helm-file-human-size (cl-getf it :size))) + (modif (cl-getf it :modif-time)) + (access (cl-getf it :access-time)) + (ext (helm-get-default-program-for-file candidate)) + (tooltip-hide-delay (or helm-tooltip-hide-delay tooltip-hide-delay))) + (if (and (display-graphic-p) tooltip-mode) + (tooltip-show + (concat + (helm-basename candidate) "\n" + dired-line "\n" + (format "Mode: %s\n" (helm-get-default-mode-for-file candidate)) + (format "Ext prog: %s\n" (or (and ext (replace-regexp-in-string + " %s" "" ext)) + "Not defined")) + (format "Type: %s: %s\n" type mode-type) + (when (string= type "symlink") + (format "True name: '%s'\n" + (cond ((string-match "^\.#" (helm-basename candidate)) + "Autosave symlink") + ((helm-ff-valid-symlink-p candidate) + (file-truename candidate)) + (t "Invalid Symlink")))) + (format "Owner: %s: %s\n" owner owner-right) + (format "Group: %s: %s\n" group group-right) + (format "Others: %s\n" other-right) + (format "Size: %s\n" size) + (format "Modified: %s\n" modif) + (format "Accessed: %s\n" access) + (and (stringp trash) + (format "Trash: %s\n" + (abbreviate-file-name trash))))) + (message dired-line) (sit-for 5))) + (message "Permission denied, file not readable"))) + +(defun helm-ff-properties-persistent () + "Show properties without quitting helm." + (interactive) + (with-helm-alive-p + (helm-attrset 'properties-action '(helm-ff-properties . never-split)) + (helm-execute-persistent-action 'properties-action))) +(put 'helm-ff-properties-persistent 'helm-only t) + +(defun helm-ff-persistent-delete () + "Delete current candidate without quitting." + (interactive) + (with-helm-alive-p + (helm-attrset 'quick-delete '(helm-ff-quick-delete . never-split)) + (helm-execute-persistent-action 'quick-delete))) +(put 'helm-ff-persistent-delete 'helm-only t) + +(defun helm-ff-dot-file-p (file) + "Check if FILE is `.' or `..'." + (member (helm-basename file) '("." ".."))) + +(defun helm-ff-kill-buffer-fname (candidate) + (let* ((buf (get-file-buffer candidate)) + (buf-name (buffer-name buf))) + (cond ((and buf (eq buf (get-buffer helm-current-buffer))) + (user-error + "Can't kill `helm-current-buffer' without quitting session")) + (buf (kill-buffer buf) (message "Buffer `%s' killed" buf-name)) + (t (message "No buffer to kill"))))) + +(defun helm-ff-kill-or-find-buffer-fname (candidate) + "Find file CANDIDATE or kill it's buffer if it is visible. +Never kill `helm-current-buffer'. +Never kill buffer modified. +This is called normally on third hit of \ +\\\\[helm-execute-persistent-action] +in `helm-find-files-persistent-action-if'." + (let* ((buf (get-file-buffer candidate)) + (buf-name (buffer-name buf)) + (win (get-buffer-window buf)) + (helm--reading-passwd-or-string t)) + (cond ((and buf win (eq buf (get-buffer helm-current-buffer))) + (user-error + "Can't kill `helm-current-buffer' without quitting session")) + ((and buf win (buffer-modified-p buf)) + (message "Can't kill modified buffer, please save it before")) + ((and buf win) + (kill-buffer buf) + (if (and helm-persistent-action-display-window + (window-dedicated-p (next-window win 1))) + (delete-window helm-persistent-action-display-window) + (set-window-buffer win helm-current-buffer)) + (message "Buffer `%s' killed" buf-name)) + (t (find-file candidate))))) + +(defun helm-ff-run-kill-buffer-persistent () + "Execute `helm-ff-kill-buffer-fname' without quitting." + (interactive) + (with-helm-alive-p + (helm-attrset 'kill-buffer-fname 'helm-ff-kill-buffer-fname) + (helm-execute-persistent-action 'kill-buffer-fname))) +(put 'helm-ff-run-kill-buffer-persistent 'helm-only t) + +;; Preview with external tool +(defun helm-ff-persistent-open-file-externally (file) + (require 'helm-external) + (if (helm-get-default-program-for-file file) + (helm-open-file-externally file) + (message "Please configure an external program for `*%s' file in `helm-external-programs-associations'" + (file-name-extension file t)))) + +(defun helm-ff-run-preview-file-externally () + (interactive) + (with-helm-alive-p + (helm-attrset 'open-file-externally '(helm-ff-persistent-open-file-externally . never-split)) + (helm-execute-persistent-action 'open-file-externally))) +(put 'helm-ff-run-preview-file-externally 'helm-only t) + +(defun helm-ff-prefix-filename (fname &optional file-or-symlinkp new-file) + "Return filename FNAME maybe prefixed with [?] or [@]. +If FILE-OR-SYMLINKP is non--nil this mean we assume FNAME is an +existing filename or valid symlink and there is no need to test it. +NEW-FILE when non--nil mean FNAME is a non existing file and +return FNAME prefixed with [?]." + (let* ((prefix-new (propertize + " " 'display + (propertize "[?]" 'face 'helm-ff-prefix))) + (prefix-url (propertize + " " 'display + (propertize "[@]" 'face 'helm-ff-prefix)))) + (cond (file-or-symlinkp fname) + ((or (string-match helm-ff-url-regexp fname) + (and helm--url-regexp (string-match helm--url-regexp fname))) + (concat prefix-url " " fname)) + (new-file (concat prefix-new " " fname))))) + +(defun helm-ff-score-candidate-for-pattern (real disp pattern) + (if (or (member real '("." "..")) + ;; Incomplete filenames are prefixed with two spaces, the + ;; first one beeing propertized with a 'display prop + ;; i.e. "[?] foo". + (and (string-match-p "\\`\\s-\\{2\\}" disp) + (string= real (substring-no-properties disp 2)))) + 900000 + (helm-score-candidate-for-pattern real pattern))) + +(defun helm-ff-sort-candidates-1 (candidates input) + "Sort function for `helm-source-find-files'. +Return candidates prefixed with basename of INPUT first." + (if (or (and (file-directory-p input) + (string-match "/\\'" input)) + (string-match "\\`\\$" input) + (null candidates)) + candidates + (let* ((memo-src (make-hash-table :test 'equal)) + (all (sort candidates + (lambda (s1 s2) + (let* ((score (lambda (disp real) + (helm-ff-score-candidate-for-pattern + disp real (helm-basename input)))) + ;; Reals + (r1 (helm-basename (if (consp s1) (cdr s1) s1))) + (r2 (helm-basename (if (consp s2) (cdr s2) s2))) + ;; Displays + (d1 (helm-basename (if (consp s1) (car s1) s1))) + (d2 (helm-basename (if (consp s2) (car s2) s2))) + (sc1 (or (gethash r1 memo-src) + (puthash r1 (funcall score r1 d1) memo-src))) + (sc2 (or (gethash r2 memo-src) + (puthash r2 (funcall score r2 d2) memo-src)))) + (cond ((= sc1 sc2) + (< (string-width r1) + (string-width r2))) + ((> sc1 sc2)))))))) + all))) + +(defun helm-ff-sort-candidates (candidates _source) + "Sort function for `helm-source-find-files'. +Return candidates prefixed with basename of `helm-input' first." + (helm-ff-sort-candidates-1 candidates helm-input)) + +(defun helm-ff-boring-file-p (file) + ;; Prevent user doing silly thing like + ;; adding the dotted files to boring regexps (#924). + (and helm-ff-skip-boring-files + (not (string-match "\\.$" file)) + (string-match helm-ff--boring-regexp file))) + +(defvar helm-ff--git-found-p nil) +(defun helm-ff-git-ignored-p (file) + (and helm-ff-skip-git-ignored-files + (not (file-remote-p file)) + (or helm-ff--git-found-p + (setq helm-ff--git-found-p (executable-find "git"))) + (zerop (call-process "git" nil nil nil "check-ignore" "-q" file)))) + +(defun helm-ff-filter-candidate-one-by-one (file) + "`filter-one-by-one' Transformer function for `helm-source-find-files'." + ;; Handle boring files + (let ((basename (helm-basename file)) + dot) + (unless (or (helm-ff-boring-file-p basename) + (helm-ff-git-ignored-p file)) + + ;; Handle tramp files with minimal highlighting. + (if (and (or (string-match-p helm-tramp-file-name-regexp helm-pattern) + (helm-file-on-mounted-network-p helm-pattern))) + (let* (hostp + (disp (if (and helm-ff-transformer-show-only-basename + (not (setq dot (helm-dir-is-dot file)))) + (or (setq hostp + (helm-ff--get-host-from-tramp-invalid-fname + file)) + basename) + file))) + ;; Filename with cntrl chars e.g. foo^J + ;; This will not work as long as most tramp file handlers doesn't + ;; handle such case, e.g. file-name-all-completions, + ;; directory-files, file-name-nondirectory etc... + ;; Keep it though in case they fix this upstream... + (setq disp (replace-regexp-in-string "[[:cntrl:]]" "?" disp)) + (cond (;; Dot directories . and .. + dot (propertize file 'face 'helm-ff-dotted-directory)) + ;; Directories. + ((get-text-property 1 'helm-ff-dir file) + (cons (propertize disp 'face 'helm-ff-directory) file)) + ;; Executable files. + ((get-text-property 1 'helm-ff-exe file) + (cons (propertize disp 'face 'helm-ff-executable) file)) + ;; Symlinks. + ((get-text-property 1 'helm-ff-sym file) + (cons (propertize disp 'face 'helm-ff-symlink) file)) + ;; Regular files. + ((get-text-property 1 'helm-ff-file file) + (cons (propertize disp 'face 'helm-ff-file) file)) + ;; non existing files. + (t (cons (helm-ff-prefix-filename + (propertize disp 'face 'helm-ff-file) + hostp (unless hostp 'new-file)) + file)))) + + ;; Highlight local files showing everything, symlinks, exe, + ;; dirs etc... + (let* ((disp (if (and helm-ff-transformer-show-only-basename + (not (setq dot (helm-dir-is-dot file))) + (not (and helm--url-regexp + (string-match helm--url-regexp file))) + (not (string-match helm-ff-url-regexp file))) + (or (helm-ff--get-host-from-tramp-invalid-fname file) + basename) + file)) + (attr (file-attributes file)) + (type (car attr)) + x-bit) + ;; Filename cntrl chars e.g. foo^J + (setq disp (replace-regexp-in-string "[[:cntrl:]]" "?" disp)) + (cond ((string-match "file-error" file) file) + (;; A dead symlink. + (and (stringp type) + (not (helm-ff-valid-symlink-p file)) + (not (string-match "^\\.#" basename))) + (cons (propertize disp 'face 'helm-ff-invalid-symlink) + file)) + ;; A dotted directory symlinked. + ((and dot (stringp type)) + (cons (propertize disp 'face 'helm-ff-dotted-symlink-directory) + file)) + ;; A dotted directory. + ((helm-ff-dot-file-p file) + (cons (propertize disp 'face 'helm-ff-dotted-directory) + file)) + ;; A symlink. + ((stringp type) + (cons (propertize disp 'display + (concat (propertize disp 'face 'helm-ff-symlink) + " -> " + (propertize (abbreviate-file-name type) + 'face 'helm-ff-truename))) + file)) + ;; A directory. + ((eq t type) + (cons (propertize disp 'face 'helm-ff-directory) + file)) + ;; A character device file. + ((and attr (string-match + "\\`[cp]" (setq x-bit (substring (nth 8 attr) 0 4)))) + (cons (propertize disp 'face 'helm-ff-pipe) + file)) + ;; A socket file. + ((and attr (string-match "\\`[s]" x-bit)) + (cons (propertize disp 'face 'helm-ff-socket) + file)) + ;; An executable file. + ((and attr + (string-match + "x\\'" x-bit)) + (cons (propertize disp 'face 'helm-ff-executable) + file)) + ;; An executable file with suid + ((and attr (string-match "s\\'" x-bit)) + (cons (propertize disp 'face 'helm-ff-suid) + file)) + ;; A file. + ((and attr (null type)) + (cons (propertize disp 'face 'helm-ff-file) + file)) + ;; A non--existing file. + (t (cons (helm-ff-prefix-filename + (propertize disp 'face 'helm-ff-file) nil 'new-file) + file)))))))) + +(defun helm-find-files-action-transformer (actions candidate) + "Action transformer for `helm-source-find-files'." + (let ((str-at-point (with-helm-current-buffer + (buffer-substring-no-properties + (point-at-bol) (point-at-eol))))) + (when (file-regular-p candidate) + (setq actions (helm-append-at-nth + actions '(("Checksum File" . helm-ff-checksum)) 4))) + (cond ((and (file-exists-p candidate) + (string-match "Trash/files/?\\'" (helm-basedir candidate)) + (not (member (helm-basename candidate) '("." ".."))) + (executable-find "trash")) + (helm-append-at-nth + actions + '(("Restore file(s) from trash" . helm-restore-file-from-trash) + ("Delete file(s) from trash" . helm-ff-trash-rm)) + 1)) + ((and helm--url-regexp + (not (string-match-p helm--url-regexp str-at-point)) + (not (with-helm-current-buffer (eq major-mode 'dired-mode))) + (string-match-p ":\\([0-9]+:?\\)" str-at-point)) + (append '(("Find file to line number" . helm-ff-goto-linum)) + actions)) + ((string-match (image-file-name-regexp) candidate) + (helm-append-at-nth + actions + '(("Rotate image right `M-r'" . helm-ff-rotate-image-right) + ("Rotate image left `M-l'" . helm-ff-rotate-image-left)) + 3)) + ((string-match "\\.el\\'" (helm-aif (helm-marked-candidates) + (car it) candidate)) + (helm-append-at-nth + actions + '(("Byte compile lisp file(s) `M-B, C-u to load'" + . helm-find-files-byte-compile) + ("Load File(s) `M-L'" . helm-find-files-load-files)) + 2)) + ((string-match "\\.elc?\\'" (helm-aif (helm-marked-candidates) + (car it) candidate)) + (helm-append-at-nth + actions + '(("Load File(s) `M-L'" . helm-find-files-load-files)) + 2)) + ((and (string-match "\\.html?$" candidate) + (file-exists-p candidate)) + (helm-append-at-nth + actions '(("Browse url file" . browse-url-of-file)) 2)) + ((or (string= (file-name-extension candidate) "pdf") + (string= (file-name-extension candidate) "PDF")) + (helm-append-at-nth + actions '(("Pdfgrep File(s)" . helm-ff-pdfgrep)) 4)) + (t actions)))) + +(defun helm-ff-trash-action (fn names &rest args) + "Execute a trash action FN on marked files. + +Arg NAMES is a list of strings to pass to messages +e.g. '(\"delete\" \"deleting\"), ARGS are other args to be passed to FN." + (let ((mkd (helm-marked-candidates)) + errors) + (with-helm-display-marked-candidates + helm-marked-buffer-name + (helm-ff--count-and-collect-dups (mapcar 'helm-basename mkd)) + (if (y-or-n-p (format "%s %s files from trash? " + (capitalize (car names)) + (length mkd))) + (progn + (message "%s files from trash..." (capitalize (cadr names))) + (cl-loop for f in mkd do + (condition-case err + (apply fn f args) + (error (push (format "%s" (cadr err)) errors) + nil))) + (if errors + (display-warning 'helm + (with-temp-buffer + (insert (format-time-string "%Y-%m-%d %H:%M:%S\n" + (current-time))) + (insert (format + "Failed to %s %s/%s files from trash\n" + (car names) (length errors) (length mkd))) + (insert (mapconcat 'identity errors "\n") "\n ") + (buffer-string)) + :error + "*helm restore warnings*") + (message "%s %s files from trash done" + (capitalize (cadr names)) (length mkd)))) + (message "Restoring files from trash aborted"))))) + +(defun helm-ff-trash-rm (_candidate) + "Delete marked-files from a Trash directory. + +The Trash directory should be a directory compliant with + and each file +should have its '*.trashinfo' correspondent file in Trash/info +directory." + (helm-ff-trash-action 'helm-ff-trash-rm-1 '("delete" "deleting"))) + +(defun helm-ff-trash-rm-1 (file) + (let ((info-file (concat (helm-reduce-file-name file 2) + "info/" (helm-basename file "trashinfo") + ".trashinfo"))) + (cl-assert (file-exists-p file) + nil (format "No such file or directory `%s'" + file)) + (cl-assert (file-exists-p info-file) + nil (format "No such file or directory `%s'" + info-file)) + (if (file-directory-p file) + (delete-directory file t) + (delete-file file)) + (delete-file info-file))) + +(defun helm-restore-file-from-trash (_candidate) + "Restore marked-files from a Trash directory. + +The Trash directory should be a directory compliant with + and each file +should have its '*.trashinfo' correspondent file in Trash/info +directory." + (let* ((default-directory (file-name-as-directory + helm-ff-default-directory)) + (trashed-files (helm-ff-trash-list))) + (helm-ff-trash-action 'helm-restore-file-from-trash-1 + '("restore" "restoring") + trashed-files))) + +(defun helm-restore-file-from-trash-1 (file trashed-files) + "Restore FILE from a trash directory. +Arg TRASHED-FILES is an alist of (fname_in_trash . dest) obtained with +`helm-ff-trash-list'." + ;; Emacs trash duplicate files with a unique name + .trashinfo in + ;; the filename which is wrong, only files in info directory should + ;; end with .trashinfo, so fix the filename before looking for dest name. + (let* ((fname (replace-regexp-in-string "\\.trashinfo\\'" "" file)) + (info-file (concat (helm-reduce-file-name fname 2) + "info/" + (helm-basename fname) + ".trashinfo")) + (dest-file (helm-ff--get-dest-file-from-trash + trashed-files fname))) + (cl-assert (not (file-exists-p dest-file)) nil + (format "File `%s' already exists" dest-file)) + (cl-assert dest-file nil "No such file in trash") + (rename-file file dest-file) + (delete-file info-file))) + +(defun helm-ff-trash-file-p (file) + "Return `t' when file is a trashed file." + (and (file-exists-p file) + (string-match "Trash/files/?\\'" (helm-basedir file)) + (not (member (helm-basename file) '("." ".."))))) + +(defun helm-ff--get-dest-file-from-trash (trashed-files file) + (assoc-default (helm-basename file) trashed-files)) + +(defun helm-ff-trash-list () + "Return an alist of trashed files basename and dest name." + (cl-loop for f in (directory-files + (expand-file-name + ;; helm-ff-default-directory is actually the + ;; trash directory. + "info" (helm-basedir (directory-file-name helm-ff-default-directory))) + t directory-files-no-dot-files-regexp) + collect (cons (helm-basename (replace-regexp-in-string "\\.trashinfo\\'" "" f)) + (with-temp-buffer + (save-excursion + (insert-file-contents f)) + (when (re-search-forward "^path=" nil t) + (helm-url-unhex-string + (buffer-substring-no-properties + (point) (point-at-eol)))))))) + +(defun helm-ff-goto-linum (candidate) + "Find file CANDIDATE and maybe jump to line number found in fname at point. +line number should be added at end of fname preceded with \":\". +e.g \"foo:12\"." + (let ((linum (with-helm-current-buffer + (let ((str (buffer-substring-no-properties + (point-at-bol) (point-at-eol)))) + (when (string-match ":\\([0-9]+:?\\)" str) + (match-string 1 str)))))) + (find-file candidate) + (and linum (not (string= linum "")) + (helm-goto-line (string-to-number linum) t)))) + +(defun helm-ff-mail-attach-files (_candidate) + "Run `mml-attach-file' on `helm-marked-candidates'." + (require 'mml) + (let ((flist (helm-marked-candidates :with-wildcard t)) + (dest-buf (and (derived-mode-p 'message-mode 'mail-mode) + (current-buffer))) + bufs) + (unless dest-buf + (setq bufs (cl-loop for b in (buffer-list) + when (with-current-buffer b + (derived-mode-p 'message-mode 'mail-mode)) + collect (buffer-name b))) + (if (and bufs (y-or-n-p "Attach files to existing mail composition buffer? ")) + (setq dest-buf + (if (cdr bufs) + (helm-comp-read "Attach to buffer: " bufs :nomark t) + (car bufs))) + (compose-mail) + (setq dest-buf (current-buffer)))) + (switch-to-buffer dest-buf) + (save-restriction + (widen) + (save-excursion + (goto-char (point-max)) + (cl-loop for f in flist + do (mml-attach-file f (or (mm-default-file-encoding f) + "application/octet-stream"))))))) + +(defvar image-dired-display-image-buffer) +(defun helm-ff-rotate-current-image-1 (file num-arg) + "Rotate current image at NUM-ARG degrees." + (setq file (file-truename file)) ; For symlinked images. + ;; When FILE is not an image-file, do nothing. + (when (and (file-exists-p file) + (string-match (image-file-name-regexp) file)) + (setq num-arg (if (string= helm-ff-rotate-image-program "exiftran") + (cl-case num-arg + (90 "-9") ; 90 clockwise + (270 "-2")) ; 270 clockwise == -90 + (number-to-string num-arg))) + (if (executable-find helm-ff-rotate-image-program) + (let ((default-directory (file-name-directory file)) + (basename (helm-basename file))) + (apply #'process-file helm-ff-rotate-image-program nil nil nil + (append helm-ff-rotate-image-switch + (list num-arg basename))) + (when (buffer-live-p image-dired-display-image-buffer) + (kill-buffer image-dired-display-image-buffer)) + (image-dired-display-image basename) + (message nil) + (display-buffer (get-buffer image-dired-display-image-buffer))) + (error "%s not found" helm-ff-rotate-image-program)))) + +(defun helm-ff-rotate-image-left (candidate) + "Rotate image file CANDIDATE left. +This affect directly file CANDIDATE." + (helm-ff-rotate-current-image-1 candidate 270)) + +(defun helm-ff-rotate-image-right (candidate) + "Rotate image file CANDIDATE right. +This affect directly file CANDIDATE." + (helm-ff-rotate-current-image-1 candidate 90)) + +(defun helm-ff-rotate-left-persistent () + "Rotate image left without quitting helm." + (interactive) + (with-helm-alive-p + (helm-attrset 'image-action1 'helm-ff-rotate-image-left) + (helm-execute-persistent-action 'image-action1))) +(put 'helm-ff-rotate-left-persistent 'helm-only t) + +(defun helm-ff-rotate-right-persistent () + "Rotate image right without quitting helm." + (interactive) + (with-helm-alive-p + (helm-attrset 'image-action2 'helm-ff-rotate-image-right) + (helm-execute-persistent-action 'image-action2))) +(put 'helm-ff-rotate-right-persistent 'helm-only t) + +(defun helm-ff-exif-data (candidate) + "Extract exif data from file CANDIDATE using `helm-ff-exif-data-program'." + (if (and helm-ff-exif-data-program + (executable-find helm-ff-exif-data-program)) + (shell-command-to-string (format "%s %s %s" + helm-ff-exif-data-program + helm-ff-exif-data-program-args + candidate)) + (format "No program %s found to extract exif" + helm-ff-exif-data-program))) + +(cl-defun helm-find-files-persistent-action-if (candidate) + "Open subtree CANDIDATE without quitting helm. +If CANDIDATE is not a directory expand CANDIDATE filename. +If CANDIDATE is alone, open file CANDIDATE filename. +That's mean: +First hit on C-j expand CANDIDATE second hit open file. +If a prefix arg is given or `helm-follow-mode' is on open file." + (let* ((follow (or (helm-follow-mode-p) + helm--temp-follow-flag)) + (image-cand (string-match-p (image-file-name-regexp) candidate)) + (new-pattern (helm-get-selection)) + (num-lines-buf (with-current-buffer helm-buffer + (count-lines (point-min) (point-max)))) + (insert-in-minibuffer (lambda (fname) + (with-selected-window (or (active-minibuffer-window) + (minibuffer-window)) + (unless follow + (delete-minibuffer-contents) + (set-text-properties 0 (length fname) + nil fname) + (insert fname)))))) + (helm-attrset 'candidate-number-limit helm-ff-candidate-number-limit) + (unless image-cand + (when follow + (helm-follow-mode -1) + (cl-return-from helm-find-files-persistent-action-if + (message "Helm-follow-mode allowed only on images, disabling")))) + (cond ((and (helm-ff--invalid-tramp-name-p) + (string-match helm-tramp-file-name-regexp candidate)) + (cons (lambda (_candidate) + ;; First hit insert hostname and + ;; second hit insert ":" and expand. + (if (string= candidate helm-pattern) + (funcall insert-in-minibuffer (concat candidate ":")) + (funcall insert-in-minibuffer candidate))) + 'never-split)) + (;; A symlink directory, expand it but not to its truename + ;; unless a prefix arg is given. + (and (file-directory-p candidate) (file-symlink-p candidate)) + (cons (lambda (_candidate) + (funcall insert-in-minibuffer + (file-name-as-directory + (if current-prefix-arg + (file-truename (expand-file-name candidate)) + (expand-file-name candidate))))) + 'never-split)) + ;; A directory, open it. + ((file-directory-p candidate) + (cons (lambda (_candidate) + (when (string= (helm-basename candidate) "..") + (setq helm-ff-last-expanded helm-ff-default-directory)) + (funcall insert-in-minibuffer (file-name-as-directory + (expand-file-name candidate)))) + 'never-split)) + ;; A symlink file, expand to it's true name. (first hit) + ((and (file-symlink-p candidate) (not current-prefix-arg) (not follow)) + (cons (lambda (_candidate) + (funcall insert-in-minibuffer (file-truename candidate)) + (helm-check-minibuffer-input)) ; Force update. + 'never-split)) + ;; A regular file, expand it, (first hit) + ((and (>= num-lines-buf 3) (not current-prefix-arg) (not follow)) + (cons (lambda (_candidate) + (funcall insert-in-minibuffer new-pattern) + (helm-check-minibuffer-input)) ; Force update. + 'never-split)) + ;; An image file and it is the second hit on C-j, + ;; show the file in `image-dired'. + (image-cand + (lambda (_candidate) + (require 'image-dired) + (let* ((win (get-buffer-window + image-dired-display-image-buffer 'visible)) + (fname (and win + (with-selected-window win + (get-text-property (point-min) + 'original-file-name)))) + (remove-buf-only (and win + fname + (with-helm-buffer + (file-equal-p candidate fname))))) + (when remove-buf-only + (with-helm-window + (if (and helm-persistent-action-display-window + (window-dedicated-p (next-window win 1))) + (delete-window helm-persistent-action-display-window) + (set-window-buffer win helm-current-buffer)))) + (when (buffer-live-p (get-buffer image-dired-display-image-buffer)) + (kill-buffer image-dired-display-image-buffer)) + (unless remove-buf-only + ;; Fix emacs bug never fixed upstream. + (unless (file-directory-p image-dired-dir) + (make-directory image-dired-dir)) + (switch-to-buffer image-dired-display-image-buffer) + (message "Resizing image...") + (cl-letf (((symbol-function 'message) #'ignore)) + (image-dired-display-image candidate)) + (message "Resizing image done") + (with-current-buffer image-dired-display-image-buffer + (let ((exif-data (helm-ff-exif-data candidate))) + (setq default-directory helm-ff-default-directory) + (image-dired-update-property 'help-echo exif-data))))))) + ;; Allow browsing archive on avfs fs. + ;; Assume volume is already mounted with mountavfs. + ((helm-aand helm-ff-avfs-directory + (file-name-directory candidate) + (string-match + (regexp-quote (expand-file-name helm-ff-avfs-directory)) + it) + (helm-ff-file-compressed-p candidate)) + (cons (lambda (_candidate) + (funcall insert-in-minibuffer (concat candidate "#/"))) + 'never-split)) + ;; File doesn't exists and basename starts with ".." or " ", + ;; Start a recursive search for directories. + ((and (not (file-exists-p candidate)) + (not (file-remote-p candidate)) + (string-match-p "\\`\\([.]\\|\\s-\\)\\{2\\}[^/]+" + (helm-basename candidate))) + ;; As soon as the final "/" is added the job is passed + ;; to `helm-ff-auto-expand-to-home-or-root'. + (cons (lambda (_candidate) + (funcall insert-in-minibuffer (concat candidate "/"))) + 'never-split)) + ;; File is not existing and have no basedir, typically when + ;; user hit C-k (minibuffer is empty) and then write foo and + ;; hit C-j. This make clear that when no basedir, helm will + ;; create the file in default-directory. + ((and (not (file-exists-p candidate)) + (not (helm-basedir candidate))) + (cons (lambda (_candidate) + (funcall insert-in-minibuffer + (expand-file-name candidate default-directory))) + 'never-split)) + ;; On second hit we open file. + ;; On Third hit we kill it's buffer maybe. + (t + (lambda (_candidate) + (funcall helm-ff-kill-or-find-buffer-fname-fn candidate)))))) + + +;;; Recursive dirs completion +;; +(defun helm-find-files-recursive-dirs (directory &optional input) + (when (string-match "\\(\\s-+\\|[.]\\)\\{2\\}" input) + (setq input (replace-match "" nil t input))) + (message "Recursively searching %s from %s ..." + input (abbreviate-file-name directory)) + ;; Ensure to not create a new frame + (let (helm-actions-inherit-frame-settings) + (helm :sources + (helm-make-source + "Recursive directories" 'helm-locate-subdirs-source + :basedir (if (string-match-p + "\\`es" helm-locate-recursive-dirs-command) + directory + (shell-quote-argument directory)) + :subdir (shell-quote-argument input) + :candidate-transformer + `((lambda (candidates) + (cl-loop for c in candidates + when (and (file-directory-p c) + (null (helm-boring-directory-p + c helm-boring-file-regexp-list)) + (string-match-p ,(regexp-quote input) + (helm-basename c))) + collect (propertize c 'face 'helm-ff-dirs))) + helm-w32-pathname-transformer + (lambda (candidates) + (helm-ff-sort-candidates-1 candidates ,input))) + :persistent-action 'ignore + :action (lambda (c) + (helm-set-pattern + (file-name-as-directory (expand-file-name c))))) + :candidate-number-limit 999999 + :allow-nest t + :resume 'noresume + :ff-transformer-show-only-basename nil + :buffer "*helm recursive dirs*"))) + +(defun helm-ff-recursive-dirs (_candidate) + "Launch a recursive search in `helm-ff-default-directory'." + (with-helm-default-directory helm-ff-default-directory + (helm-find-files-recursive-dirs + (helm-current-directory) + (helm-basename (helm-get-selection))))) + +(defun helm-ff-file-compressed-p (candidate) + "Whether CANDIDATE is a compressed file or not." + (member (file-name-extension candidate) + helm-ff-file-compressed-list)) + +(defun helm-ff--fname-at-point () + "Try to guess fname at point." + (let ((end (point)) + (limit (helm-aif (bounds-of-thing-at-point 'filename) + (car it) + (point)))) + (save-excursion + (while (re-search-backward "\\(~\\|/\\|[[:lower:][:upper:]]:/\\)" + limit t)) + (buffer-substring-no-properties (point) end)))) + +(defun helm-insert-file-name-completion-at-point (_candidate) + "Insert file name completion at point. + +When completing i.e. there is already something at point, insert +filename abbreviated, relative or full according to initial input, +whereas when inserting i.e. there is nothing at point, insert filename +full, abbreviated or relative according to prefix arg, respectively no +prefix arg, one prefix arg or two prefix arg." + (with-helm-current-buffer + (if buffer-read-only + (error "Error: Buffer `%s' is read-only" (buffer-name)) + (let* ((mkds (helm-marked-candidates :with-wildcard t)) + (candidate (car mkds)) + (end (point)) + (tap (helm-ffap-guesser)) + (guess (and (stringp tap) + (substring-no-properties tap))) + (beg (if guess (- (point) (length guess)) (point))) + (full-path-p (and (stringp guess) + (or (string-match-p + (concat "^" (getenv "HOME")) + guess) + (string-match-p + "\\`\\(/\\|[[:lower:][:upper:]]:/\\)" + guess)))) + (escape-fn (with-helm-current-buffer + (if (memq major-mode + helm-modes-using-escaped-strings) + #'shell-quote-argument #'identity)))) + (insert + (funcall escape-fn (helm-ff--insert-fname + candidate beg end full-path-p guess)) + (if (cdr mkds) " " "") + (mapconcat escape-fn + (cl-loop for f in (cdr mkds) + collect (helm-ff--insert-fname f)) + " ")))))) + +(defun helm-ff--insert-fname (candidate &optional beg end full-path guess) + (set-text-properties 0 (length candidate) nil candidate) + (if (and beg end guess (not (string= guess "")) + (or (string-match + "^\\(~/\\|/\\|[[:lower:][:upper:]]:/\\)" + guess) + (file-exists-p candidate))) + (prog1 + (cond (full-path + (expand-file-name candidate)) + ((string= (match-string 1 guess) "~/") + (abbreviate-file-name candidate)) + (t (file-relative-name candidate))) + (delete-region beg end)) + (helm-acase helm-current-prefix-arg + ('(4) (abbreviate-file-name candidate)) + ('(16) (file-relative-name candidate)) + ('(64) (helm-basename candidate)) + (t candidate)))) + +(cl-defun helm-find-files-history (arg &key (comp-read t)) + "The `helm-find-files' history. +Show the first `helm-ff-history-max-length' elements of +`helm-ff-history' in an `helm-comp-read'." + (interactive "p") + (let ((history (when helm-ff-history + (helm-fast-remove-dups helm-ff-history + :test 'equal)))) + (when history + (setq helm-ff-history + (if (>= (length history) helm-ff-history-max-length) + (cl-subseq history 0 helm-ff-history-max-length) + history)) + (if comp-read + (let ((src (helm-build-sync-source "Helm Find Files History" + :candidates helm-ff-history + :fuzzy-match (helm-ff-fuzzy-matching-p) + :persistent-action 'ignore + :migemo t + :action (lambda (candidate) + (if arg + (helm-set-pattern + (expand-file-name candidate)) + (identity candidate)))))) + (helm :sources src + :resume 'noresume + :buffer helm-ff-history-buffer-name + :allow-nest t)) + helm-ff-history)))) +(put 'helm-find-files-history 'helm-only t) + +(defun helm-find-files-1 (fname &optional preselect) + "Find FNAME filename with PRESELECT filename preselected. + +Use it for non--interactive calls of `helm-find-files'." + (require 'tramp) + ;; Resolve FNAME now outside of helm. + ;; [FIXME] When `helm-find-files-1' is used directly from lisp + ;; and FNAME is an abbreviated path, for some reasons + ;; `helm-update' is called many times before resolving + ;; the abbreviated path (Issue #1939) so be sure to pass a + ;; full path to helm-find-files-1. + (unless (string-match-p helm-ff-url-regexp fname) + (setq fname (expand-file-name (substitute-in-file-name fname)))) + (when (get-buffer helm-action-buffer) + (kill-buffer helm-action-buffer)) + (setq helm-find-files--toggle-bookmark nil) + (let* ( ;; Be sure we don't erase the precedent minibuffer if some. + (helm-ff-auto-update-initial-value + (and helm-ff-auto-update-initial-value + (not (minibuffer-window-active-p (minibuffer-window))))) + (tap (thing-at-point 'filename)) + (def (and tap (or (file-remote-p tap) + (expand-file-name tap))))) + (helm-set-local-variable 'helm-follow-mode-persistent nil) + (unless helm-source-find-files + (setq helm-source-find-files (helm-make-source + "Find Files" 'helm-source-ffiles))) + (when (helm-attr 'follow helm-source-find-files) + (helm-attrset 'follow -1 helm-source-find-files)) + (helm-ff-setup-update-hook) + (add-hook 'helm-resume-after-hook 'helm-ff--update-resume-after-hook) + (unwind-protect + (helm :sources 'helm-source-find-files + :input fname + :case-fold-search helm-file-name-case-fold-search + :preselect preselect + :ff-transformer-show-only-basename + helm-ff-transformer-show-only-basename + :default def + :prompt "Find files or url: " + :buffer "*helm find files*") + (helm-ff--update-resume-after-hook nil t) + (setq helm-ff-default-directory nil)))) + +(defun helm-ff--update-resume-after-hook (sources &optional nohook) + "Meant to be used in `helm-resume-after-hook'. +When NOHOOK is non nil run inconditionally, otherwise only when source +is helm-source-find-files." + (when (or nohook (string= "Find Files" + (assoc-default 'name (car sources)))) + (helm-attrset 'resume `(lambda () + (helm-ff-setup-update-hook) + (setq helm-ff-default-directory + ,helm-ff-default-directory + helm-ff-last-expanded + ,helm-ff-last-expanded)) + helm-source-find-files))) + +(defun helm-ff-clean-initial-input () + ;; When using hff in an external frame initial input is printed in + ;; the minibuffer of initial-frame, delete it. + (with-selected-frame helm-initial-frame + (helm-clean-up-minibuffer))) + +(defun helm-ff-setup-update-hook () + (dolist (hook '(helm-ff-clean-initial-input ; Add to be called first. + helm-ff-move-to-first-real-candidate + helm-ff-update-when-only-one-matched + helm-ff-auto-expand-to-home-or-root)) + (add-hook 'helm-after-update-hook hook))) + +(defun helm-find-files-cleanup () + (mapc (lambda (hook) + (remove-hook 'helm-after-update-hook hook)) + '(helm-ff-auto-expand-to-home-or-root + helm-ff-update-when-only-one-matched + helm-ff-move-to-first-real-candidate + helm-ff-clean-initial-input))) + +(defun helm-ff-bookmark () + (helm :sources 'helm-source-bookmark-helm-find-files + :buffer "*helm ff bookmarks*")) + +(defun helm-find-files-switch-to-bookmark () + "Switch to helm-bookmark for `helm-find-files' from `helm-find-files.'" + (interactive) + (require 'helm-bookmark) + (with-helm-alive-p + (helm-run-after-exit 'helm-ff-bookmark))) +(put 'helm-find-files-switch-to-bookmark 'helm-only t) + +(defun helm-find-files-initial-input (&optional input) + "Return INPUT if present, otherwise try to guess it." + (let ((guesser (helm-acase (helm-ffap-guesser) + ("" nil) + (t it)))) + (unless (eq major-mode 'image-mode) + (or (and input (or (and (file-remote-p input) input) + (expand-file-name input))) + (helm-find-files-input + (if (and helm-ff-allow-non-existing-file-at-point + guesser + (not (string-match ffap-url-regexp guesser))) + ;; Keep the ability of jumping to numbered lines even + ;; when allowing non existing filenames at point. + (helm-aand guesser + (thing-at-point 'filename) + (replace-regexp-in-string + ":[0-9]+\\'" "" it)) + guesser) + (thing-at-point 'filename)))))) + +(defun helm-ffap-guesser () + "Same as `ffap-guesser' but without gopher and machine support." + (require 'ffap) + ;; Avoid "Stack overflow in regexp matcher" error + ;; in evil `ffap-guesser' by removing crap `ffap-gopher-at-point' + ;; (bug fixed in emacs-26 #25391) . + ;; `ffap-machine-at-point' have been removed too as it was anyway + ;; disabled with `ffap-machine-p-known' bound to 'reject. + ;; `ffap-file-at-point' can be neutralized with + ;; `helm-ff-guess-ffap-filenames' and `ffap-url-at-point' with + ;; `helm-ff-guess-ffap-urls' + ;; Note also that `ffap-url-unwrap-remote' can override these + ;; variables. + (let ((ffap-alist (and helm-ff-guess-ffap-filenames ffap-alist)) + (ffap-url-regexp helm--url-regexp)) + (if (eq major-mode 'dired-mode) + (let ((beg (save-excursion (dired-move-to-filename))) + (end (save-excursion (dired-move-to-end-of-filename t)))) + (helm-aif (and beg end (member (buffer-substring beg end) + '("." ".."))) + (concat (file-name-as-directory + (expand-file-name dired-directory)) + (car it)) + (dired-get-filename 'no-dir t))) + (let* ((beg (and (use-region-p) (region-beginning))) + (end (and (use-region-p) (region-end))) + (str (and beg end (buffer-substring-no-properties beg end))) + (ffap (or (helm-aand helm-ff-guess-ffap-urls ffap-url-regexp + (ffap-fixup-url (ffap-url-at-point)) + (and (string-match ffap-url-regexp it) it)) + (ffap-file-at-point)))) + ;; Workaround emacs bugs: + ;; When the region is active and a file is detected + ;; `ffap-string-at-point' returns the region prefixed with + ;; "/", e.g. at a beginning of a patch (first bug) and make + ;; `file-remote-p' returning an error (second bug), so in such + ;; case returns the region itself instead of the region + ;; corrupted by ffap. + (if (and str ffap) str ffap))))) + +(defun helm-find-files-input (file-at-pt thing-at-pt) + "Try to guess a default input for `helm-find-files'." + (let* ((non-essential t) + (remp (or (and file-at-pt (file-remote-p file-at-pt)) + (and thing-at-pt (file-remote-p thing-at-pt)))) + (def-dir (helm-current-directory)) + (urlp (and file-at-pt helm--url-regexp + (string-match helm--url-regexp file-at-pt))) + (lib (when helm-ff-search-library-in-sexp + (helm-find-library-at-point))) + (hlink (helm-ff-find-url-at-point)) + (file-p (and file-at-pt + (not (string= file-at-pt "")) + (not remp) + (or (file-exists-p file-at-pt) + helm-ff-allow-non-existing-file-at-point) + (not urlp) + thing-at-pt + (not (string= thing-at-pt "")) + (file-exists-p + (file-name-directory + (expand-file-name thing-at-pt def-dir)))))) + (cond (lib) ; e.g we are inside a require sexp. + (hlink) ; String at point is an hyperlink. + (file-p ; a regular file + (and file-at-pt (if (not (member (helm-basename file-at-pt) + '("." ".."))) + (expand-file-name file-at-pt) + file-at-pt))) + (urlp (helm-html-decode-entities-string file-at-pt)) ; possibly an url or email. + ((and file-at-pt + (not remp) + (or helm-ff-allow-non-existing-file-at-point + (file-exists-p file-at-pt))) + (expand-file-name file-at-pt))))) + +(defun helm-ff-find-url-at-point () + "Try to find link to an url in text-property at point." + (let* ((he (get-text-property (point) 'help-echo)) + (ov (overlays-at (point))) + (ov-he (and ov (overlay-get + (car (overlays-at (point))) 'help-echo))) + (w3m-l (get-text-property (point) 'w3m-href-anchor)) + (nt-prop (get-text-property (point) 'nt-link))) + ;; Org link. + (when (and (stringp he) (string-match "^LINK: " he)) + (setq he (replace-match "" t t he))) + (cl-loop for i in (list he ov-he w3m-l nt-prop) + thereis (and (stringp i) helm--url-regexp (string-match helm--url-regexp i) i)))) + +(defun helm-find-library-at-point () + "Try to find library path at point. +Find inside `require' and `declare-function' sexp." + (require 'find-func) + (let* ((beg-sexp (save-excursion (search-backward "(" (point-at-bol) t))) + (end-sexp (save-excursion (search-forward ")" (point-at-eol) t))) + (sexp (and beg-sexp end-sexp + (buffer-substring-no-properties + (1+ beg-sexp) (1- end-sexp))))) + (ignore-errors + (cond ((and sexp (string-match "require ['].+[^)]" sexp)) + (find-library-name + (replace-regexp-in-string + "'\\|)\\|(" "" + ;; If require use third arg, ignore it, + ;; always use library path found in `load-path'. + (cl-second (split-string (match-string 0 sexp)))))) + ((and sexp (string-match-p "^declare-function" sexp)) + (find-library-name + (replace-regexp-in-string + "\"\\|ext:" "" + (cl-third (split-string sexp))))) + (t nil))))) + + +;;; Handle copy, rename, symlink, relsymlink and hardlink from helm. +;; +;; +(defun helm-ff--valid-default-directory () + (with-helm-current-buffer + (cl-loop for b in (buffer-list) + for cd = (with-current-buffer b default-directory) + when (eq (car (file-attributes cd)) t) + return cd))) + +(cl-defun helm-dired-action (candidate + &key action follow (files (dired-get-marked-files))) + "Execute ACTION on FILES to CANDIDATE. +Where ACTION is a symbol that can be one of: +'copy, 'rename, 'symlink,'relsymlink, 'hardlink or 'backup. +Argument FOLLOW when non--nil specify to follow FILES to destination for the actions +copy and rename." + (require 'dired-async) + (require 'dired-x) ; For dired-keep-marker-relsymlink + (when (get-buffer dired-log-buffer) (kill-buffer dired-log-buffer)) + ;; When default-directory in current-buffer is an invalid directory, + ;; (e.g buffer-file directory have been renamed somewhere else) + ;; be sure to use a valid value to give to dired-create-file. + ;; i.e start-process is creating a process buffer based on default-directory. + (let ((default-directory (helm-ff--valid-default-directory)) + (fn (cl-case action + (copy 'dired-copy-file) + (rename 'dired-rename-file) + (symlink 'make-symbolic-link) + (relsymlink 'dired-make-relative-symlink) + (hardlink 'dired-hardlink) + (backup 'backup-file))) + (marker (cl-case action + ((copy rename backup) dired-keep-marker-copy) + (symlink dired-keep-marker-symlink) + (relsymlink dired-keep-marker-relsymlink) + (hardlink dired-keep-marker-hardlink))) + (dirflag (and (= (length files) 1) + (file-directory-p (car files)) + (not (file-directory-p candidate)))) + (dired-async-state (if (and (boundp 'dired-async-mode) + dired-async-mode) + 1 -1))) + (and follow (fboundp 'dired-async-mode) (dired-async-mode -1)) + (when (and (cdr files) (not (file-directory-p candidate))) + (error "%s: target `%s' is not a directory" action candidate)) + (unwind-protect + (dired-create-files + fn (symbol-name action) files + ;; CANDIDATE is the destination. + (if (file-directory-p candidate) + ;; When CANDIDATE is a directory, build file-name in this directory. + ;; Else we use CANDIDATE. + (lambda (from) + (expand-file-name (file-name-nondirectory from) candidate)) + (lambda (_from) candidate)) + marker) + (and (fboundp 'dired-async-mode) + (dired-async-mode dired-async-state))) + (push (file-name-as-directory + (if (file-directory-p candidate) + (expand-file-name candidate) + (file-name-directory candidate))) + helm-ff-history) + ;; If follow is non--nil we should not be in async mode. + (when (and follow + (not (memq action '(symlink relsymlink hardlink))) + (not (get-buffer dired-log-buffer))) + (let ((target (directory-file-name candidate))) + (unwind-protect + (progn + (setq helm-ff-cand-to-mark + (helm-get-dest-fnames-from-list files candidate dirflag)) + (with-helm-after-update-hook (helm-ff-maybe-mark-candidates)) + (if (and dirflag (eq action 'rename)) + (helm-find-files-1 (file-name-directory target) + (if helm-ff-transformer-show-only-basename + (helm-basename target) target)) + (helm-find-files-1 (file-name-as-directory + (expand-file-name candidate))))) + (setq helm-ff-cand-to-mark nil)))))) + +(defun helm-get-dest-fnames-from-list (flist dest-cand rename-dir-flag) + "Transform filenames of FLIST to abs of DEST-CAND. +If RENAME-DIR-FLAG is non--nil collect the `directory-file-name' of transformed +members of FLIST." + ;; At this point files have been renamed/copied at destination. + ;; That's mean DEST-CAND exists. + (cl-loop + with dest = (expand-file-name dest-cand) + for src in flist + for basename-src = (helm-basename src) + for fname = (cond (rename-dir-flag (directory-file-name dest)) + ((file-directory-p dest) + (concat (file-name-as-directory dest) basename-src)) + (t dest)) + when (file-exists-p fname) + collect fname into tmp-list + finally return (sort tmp-list 'string<))) + +(defun helm-ff-maybe-mark-candidates () + "Mark all candidates of list `helm-ff-cand-to-mark'. +This is used when copying/renaming/symlinking etc... and +following files to destination." + (when (and (string= (assoc-default 'name (helm-get-current-source)) + (assoc-default 'name helm-source-find-files)) + helm-ff-cand-to-mark) + (with-helm-window + (while helm-ff-cand-to-mark + (if (string= (car helm-ff-cand-to-mark) (helm-get-selection)) + (progn + (helm-make-visible-mark) + (helm-next-line) + (setq helm-ff-cand-to-mark (cdr helm-ff-cand-to-mark))) + (helm-next-line))) + (unless (helm-this-visible-mark) + (helm-prev-visible-mark))))) + + +;;; Routines for files +;; +;; +(defun helm-file-buffers (filename) + "Returns a list of buffer names corresponding to FILENAME." + (cl-loop with name = (expand-file-name filename) + for buf in (buffer-list) + for bfn = (buffer-file-name buf) + when (and bfn (string= name bfn)) + collect (buffer-name buf))) + +(defun helm-ff--delete-by-moving-to-trash (file) + "Decide to trash or delete FILE. +Returns non-nil when FILE needs to be trashed." + (let ((remote (file-remote-p file))) + (or + (and delete-by-moving-to-trash + (null helm-current-prefix-arg) + (null current-prefix-arg) + (or (and remote helm-trash-remote-files) + (null remote))) + (and (null delete-by-moving-to-trash) + (or helm-current-prefix-arg + current-prefix-arg) + (or (and remote helm-trash-remote-files) + (null remote)))))) + +(defun helm-ff-quick-delete (_candidate) + "Delete file CANDIDATE without quitting. + +When a prefix arg is given, meaning of `delete-by-moving-to-trash' is +inversed." + (with-helm-window + (let ((marked (helm-marked-candidates))) + (unwind-protect + (cl-loop with trash = (helm-ff--delete-by-moving-to-trash (car marked)) + for c in marked do + (progn (helm-preselect + (concat "^" (regexp-quote + (if (and helm-ff-transformer-show-only-basename + (not (helm-ff-dot-file-p c))) + (helm-basename c) c)))) + (when (y-or-n-p + (format "Really %s file `%s'? " + (if trash "Trash" "Delete") + (abbreviate-file-name c))) + (helm-delete-file + c helm-ff-signal-error-on-dot-files 'synchro trash) + (helm-delete-current-selection) + (message nil) + (helm--remove-marked-and-update-mode-line c)))) + (setq helm-marked-candidates nil + helm-visible-mark-overlays nil) + (helm-force-update + (let ((presel (helm-get-selection))) + (when presel + (concat "^" (regexp-quote (if (and helm-ff-transformer-show-only-basename + (not (helm-ff-dot-file-p presel))) + (helm-basename presel) presel)))))))))) + +(defun helm-delete-file (file &optional error-if-dot-file-p synchro trash) + "Delete FILE after querying the user. + +When a prefix arg is given, meaning of `delete-by-moving-to-trash' is +inversed. + +Return error when ERROR-IF-DOT-FILE-P is non nil and user tries to +delete a dotted file i.e. \".\" or \"..\". + +Ask user when directory are not empty to allow recursive deletion +unless `helm-ff-allow-recursive-deletes' is non nil. +When user is asked and reply with \"!\" don't ask for remaining +directories. + +Ask to kill buffers associated with that file, too. + +When TRASH is non nil, trash FILE even if `delete-by-moving-to-trash' +is nil." + (require 'dired) + (cl-block nil + (when (and error-if-dot-file-p + (helm-ff-dot-file-p file)) + (error "Error: Cannot operate on `.' or `..'")) + (let ((buffers (helm-file-buffers file)) + (helm--reading-passwd-or-string t) + (file-attrs (file-attributes file)) + (trash (or trash (helm-ff--delete-by-moving-to-trash file))) + (delete-by-moving-to-trash trash)) + (cond ((and (eq (nth 0 file-attrs) t) + (directory-files file t dired-re-no-dot)) + ;; Synchro means persistent deletion from HFF. + (if synchro + (when (or helm-ff-allow-recursive-deletes + trash + (y-or-n-p (format "Recursive delete of `%s'? " + (abbreviate-file-name file)))) + (delete-directory file 'recursive trash)) + ;; Avoid using dired-delete-file really annoying in + ;; emacs-26 but allows using ! (instead of all) to not + ;; confirm anymore for recursive deletion of + ;; directory. This is not persistent for all session + ;; like emacs-26 does with dired-delete-file (think it + ;; is a bug). + (if (or helm-ff-allow-recursive-deletes trash) + (delete-directory file 'recursive trash) + (helm-acase (helm-read-answer (format "Recursive delete of `%s'? [y,n,!,q]" + (abbreviate-file-name file)) + '("y" "n" "!" "q")) + ("y" (delete-directory file 'recursive trash)) + ("!" (setq helm-ff-allow-recursive-deletes t) + (delete-directory file 'recursive trash)) + ("n" (cl-return 'skip)) + ("q" (throw 'helm-abort-delete-file + (progn + (message "Abort file deletion") (sleep-for 1)))))))) + ((eq (nth 0 file-attrs) t) + (delete-directory file nil trash)) + (t (delete-file file trash))) + (when buffers + (cl-dolist (buf buffers) + (when (y-or-n-p (format "Kill buffer %s, too? " buf)) + (kill-buffer buf))))))) + +(defun helm-delete-marked-files (_ignore) + "Delete marked files with `helm-delete-file'. + +When a prefix arg is given, meaning of `delete-by-moving-to-trash' is +inversed." + (let* ((files (helm-marked-candidates :with-wildcard t)) + (len 0) + (trash (helm-ff--delete-by-moving-to-trash (car files))) + (prmt (if trash "Trash" "Delete")) + (old--allow-recursive-deletes helm-ff-allow-recursive-deletes)) + (with-helm-display-marked-candidates + helm-marked-buffer-name + (helm-ff--count-and-collect-dups files) + (if (not (y-or-n-p (format "%s *%s File(s)" prmt (length files)))) + (message "(No deletions performed)") + (catch 'helm-abort-delete-file + (unwind-protect + (cl-dolist (i files) + (set-text-properties 0 (length i) nil i) + (let ((res (helm-delete-file + i helm-ff-signal-error-on-dot-files nil trash))) + (if (eq res 'skip) + (progn (message "Directory is not empty, skipping") + (sleep-for 1)) + (cl-incf len)))) + (setq helm-ff-allow-recursive-deletes old--allow-recursive-deletes))) + (message "%s File(s) %s" len (if trash "trashed" "deleted")))))) + +;;; Delete files async +;; +;; +(defvar helm-ff-delete-log-file + (expand-file-name "helm-delete-file.log" user-emacs-directory) + "The file use to communicate with emacs child when deleting files async.") + +(defvar helm-ff--trash-flag nil) + +(define-minor-mode helm-ff--delete-async-modeline-mode + "Notify mode-line that an async process run." + :group 'dired-async + :global t + ;; FIXME: Handle jobs like in dired-async, needs first to allow + ;; naming properly processes in async, they are actually all named + ;; emacs and running `async-batch-invoke', so if one copy a file and + ;; delete another file at the same time it may clash. + :lighter (:eval (propertize (format " %s file(s) async ..." + (if helm-ff--trash-flag + "Trashing" "Deleting")) + 'face 'helm-delete-async-message)) + (unless helm-ff--delete-async-modeline-mode + (let ((visible-bell t)) (ding)) + (setq helm-ff--trash-flag nil))) + +(defun helm-delete-async-mode-line-message (text face &rest args) + "Notify end of async operation in `mode-line'." + (message nil) + (let ((mode-line-format (concat + " " (propertize + (if args + (apply #'format text args) + text) + 'face face)))) + (force-mode-line-update) + (sit-for 3) + (force-mode-line-update))) + +(defun helm-delete-marked-files-async (_ignore) + "Same as `helm-delete-marked-files' but async. + +When a prefix arg is given, meaning of `delete-by-moving-to-trash' is +inversed. + +This function is not using `helm-delete-file' and BTW not asking user +for recursive deletion of directory, be warned that directories are +always deleted with no warnings." + (let* ((files (helm-marked-candidates :with-wildcard t)) + (trash (helm-ff--delete-by-moving-to-trash (car files))) + (prmt (if trash "Trash" "Delete")) + (buffers (cl-loop for file in files + for buf = (helm-file-buffers file) + when buf append buf)) + (callback (lambda (result) + (helm-ff--delete-async-modeline-mode -1) + (when (file-exists-p helm-ff-delete-log-file) + (display-warning 'helm + (with-temp-buffer + (insert-file-contents + helm-ff-delete-log-file) + (buffer-string)) + :error + "*helm delete files*") + (fit-window-to-buffer (get-buffer-window + "*helm delete files*")) + (delete-file helm-ff-delete-log-file)) + (when buffers + (dolist (buf buffers) + (let ((last-nonmenu-event t)) + (when (y-or-n-p (format "Kill buffer %s, too? " buf)) + (kill-buffer buf))))) + (run-with-timer + 0.1 nil + (lambda () + (helm-delete-async-mode-line-message + "%s (%s/%s) file(s) async done" + 'helm-delete-async-message + (if trash "Trashing" "Deleting") + result (length files)))))) + ;; Workaround emacs-26 bug with tramp see + ;; https://github.com/jwiegley/emacs-async/issues/80. + (async-quiet-switch "-q")) + (setq helm-ff--trash-flag trash) + (with-helm-display-marked-candidates + helm-marked-buffer-name + (helm-ff--count-and-collect-dups files) + (if (not (y-or-n-p (format "%s *%s File(s)" prmt (length files)))) + (message "(No deletions performed)") + (async-start + `(lambda () + ;; `delete-by-moving-to-trash' have to be set globally, + ;; using the TRASH argument of delete-file or + ;; delete-directory is not enough. + (setq delete-by-moving-to-trash ,trash) + (let ((result 0)) + (dolist (file ',files result) + (condition-case err + (cond ((eq (nth 0 (file-attributes file)) t) + (delete-directory file 'recursive ,trash) + (setq result (1+ result))) + (t (delete-file file ,trash) + (setq result (1+ result)))) + (error (with-temp-file ,helm-ff-delete-log-file + (insert (format-time-string "%x:%H:%M:%S\n")) + (insert (format "%s:%s\n " + (car err) + (mapconcat 'identity (cdr err) " "))))))))) + callback) + (helm-ff--delete-async-modeline-mode 1))))) + +(defun helm-find-file-or-marked (candidate) + "Open file CANDIDATE or open helm marked files in separate windows. +Called with one prefix arg open files in separate windows in a +vertical split. +Called with two prefix arg open files in background without selecting them." + (let ((marked (helm-marked-candidates :with-wildcard t)) + (url-p (and helm--url-regexp ; we should have only one candidate. + (string-match helm--url-regexp candidate))) + (ffap-newfile-prompt helm-ff-newfile-prompt-p) + (find-file-wildcards nil) + (helm--reading-passwd-or-string t)) + (if (cdr marked) + (if (equal helm-current-prefix-arg '(16)) + (mapcar 'find-file-noselect marked) + ;; If helm-current-prefix-arg is detected split is done + ;; vertically. + (helm-window-show-buffers (mapcar 'find-file-noselect marked))) + (let ((dir (and (not url-p) (helm-basedir candidate)))) + (cond ((and dir (file-directory-p dir)) + (find-file (substitute-in-file-name candidate))) + (url-p (find-file-at-point candidate)) + ;; A a non--existing filename ending with / + ;; Create a directory and jump to it. + ((and (not (file-exists-p candidate)) + (string-match "/$" candidate)) + (helm-ff--mkdir candidate 'helm-ff)) + ;; A non--existing filename NOT ending with / or + ;; an existing filename, create or jump to it. + ;; If the basedir of candidate doesn't exists, + ;; ask for creating it. + (dir + (helm-ff--mkdir dir) + (find-file candidate)) + ;; Find file at `default-directory' when basedir is + ;; unspecified e.g user hit C-k foo RET. + (t (find-file candidate))))))) + +(defun helm-ff-find-file-other-tab () + "Run find file in other tab action from `helm-source-buffers-list'." + (interactive) + (cl-assert (fboundp 'tab-bar-mode) nil "Tab-bar-mode not available") + (with-helm-alive-p + (helm-exit-and-execute-action 'find-file-other-tab))) +(put 'helm-ff-find-file-other-tab 'helm-only t) + +(defun helm-ff--mkdir (dir &optional helm-ff) + (when (or (not confirm-nonexistent-file-or-buffer) + (y-or-n-p (format "Create directory `%s'? " + (abbreviate-file-name + (expand-file-name dir))))) + (let ((dirfname (directory-file-name dir))) + (if (file-exists-p dirfname) + (error + "Mkdir: Unable to create directory `%s': file exists." + (helm-basename dirfname)) + (make-directory dir 'parent))) + (when helm-ff + ;; Allow having this new dir in history + ;; to be able to retrieve it immediately + ;; if we want to e.g copy a file from somewhere in it. + (setq helm-ff-default-directory + (file-name-as-directory (expand-file-name dir))) + (push helm-ff-default-directory helm-ff-history)) + (or (and helm-ff (helm-find-files-1 dir)) t))) + +(defun helm-transform-file-load-el (actions candidate) + "Add action to load the file CANDIDATE if it is an emacs lisp +file. Else return ACTIONS unmodified." + (if (member (file-name-extension candidate) '("el" "elc")) + (append actions '(("Load Emacs Lisp File" . load-file))) + actions)) + +(defun helm-transform-file-browse-url (actions candidate) + "Add an action to browse the file CANDIDATE if it is a html file or URL. +Else return ACTIONS unmodified." + (let ((browse-action '("Browse with Browser" . browse-url))) + (cond ((string-match "^http\\|^ftp" candidate) + (cons browse-action actions)) + ((string-match "\\.html?$" candidate) + (append actions (list browse-action))) + (t actions)))) + +(defun helm-file-on-mounted-network-p (file) + "Returns non-nil when FILE is part of a mounted remote directory. + +This function is checking `helm-mounted-network-directories' list." + (when helm-mounted-network-directories + (cl-loop for dir in helm-mounted-network-directories + thereis (file-in-directory-p file dir)))) + +;; helm-find-files bindings for filecache +(defvar file-cache-alist) + +(defun helm-ff-cache-add-file (_candidate) + (require 'filecache) + (let ((mkd (helm-marked-candidates :with-wildcard t))) + (mapc 'file-cache-add-file mkd))) + +(defun helm-ff-file-cache-remove-file-1 (file) + "Remove FILE from `file-cache-alist'." + (let ((entry (assoc (helm-basename file) file-cache-alist)) + (dir (helm-basedir file)) + new-entry) + (setq new-entry (remove dir entry)) + (when (= (length entry) 1) + (setq new-entry nil)) + (setq file-cache-alist + (cons new-entry (remove entry file-cache-alist))))) + +(defun helm-ff-file-cache-remove-file (_file) + "Remove marked files from `file-cache-alist.'" + (let ((mkd (helm-marked-candidates))) + (mapc 'helm-ff-file-cache-remove-file-1 mkd))) + + +;;; File name history +;; +;; +(defvar helm-source-file-name-history + (helm-build-sync-source "File Name History" + :candidates 'file-name-history + :persistent-action #'ignore + :filtered-candidate-transformer #'helm-file-name-history-transformer + :action 'helm-type-file-actions)) + +(defvar helm-source--ff-file-name-history nil + "[Internal] This source is build to be used with `helm-find-files'. +Don't use it in your own code unless you know what you are doing.") + +(defvar helm--file-name-history-hide-deleted nil) + +(defun helm-file-name-history-show-or-hide-deleted () + (interactive) + (setq helm--file-name-history-hide-deleted + (not helm--file-name-history-hide-deleted)) + (helm-update)) +(put 'helm-file-name-history-show-or-hide-deleted 'helm-only t) + +(defvar helm-file-name-history-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "C-c d") 'helm-file-name-history-show-or-hide-deleted) + map)) + +(defun helm-file-name-history-transformer (candidates _source) + (cl-loop for c in candidates + when (cond ((or (file-remote-p c) + (and (fboundp 'tramp-archive-file-name-p) + (tramp-archive-file-name-p c))) + (cons (propertize c 'face 'helm-history-remote) c)) + ((file-exists-p c) + (cons (propertize c 'face 'helm-ff-file) c)) + (t (unless helm--file-name-history-hide-deleted + (cons (propertize c 'face 'helm-history-deleted) c)))) + collect it)) + +(defun helm-ff-file-name-history () + "Switch to `file-name-history' without quitting `helm-find-files'." + (interactive) + (unless helm-source--ff-file-name-history + (setq helm-source--ff-file-name-history + (helm-build-sync-source "File name history" + :init (lambda () + (with-helm-alive-p + (require 'tramp-archive nil t) + (when helm-ff-file-name-history-use-recentf + (require 'recentf) + (or recentf-mode (recentf-mode 1))))) + :candidates (lambda () + (if helm-ff-file-name-history-use-recentf + recentf-list + file-name-history)) + :help-message 'helm-file-name-history-help-message + :fuzzy-match t + :persistent-action 'ignore + :migemo t + :filtered-candidate-transformer 'helm-file-name-history-transformer + :action (helm-make-actions + "Find file" (lambda (candidate) + (helm-set-pattern + (expand-file-name candidate)) + (with-helm-after-update-hook (helm-exit-minibuffer))) + "Find file in helm" (lambda (candidate) + (helm-set-pattern + (expand-file-name candidate)))) + :keymap helm-file-name-history-map))) + (with-helm-alive-p + (helm :sources 'helm-source--ff-file-name-history + :buffer "*helm-file-name-history*" + :allow-nest t + :resume 'noresume))) +(put 'helm-ff-file-name-history 'helm-only t) + +;;; Browse project +;; Need dependencies: +;; +;; +;; Only hg and git are supported for now. +(defvar helm--browse-project-cache (make-hash-table :test 'equal)) +(defvar helm-buffers-in-project-p) + +(defvar helm-browse-project-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-generic-files-map) + (define-key map (kbd "M-g a") 'helm-browse-project-run-ag) + map)) + +(defun helm-browse-project-get-buffers (root-directory) + (cl-loop for b in (helm-buffer-list) + ;; FIXME: Why default-directory is root-directory + ;; for current-buffer when coming from helm-quit-and-find-file. + for cd = (with-current-buffer b default-directory) + for bn = (buffer-file-name (get-buffer b)) + if (or (and bn (file-in-directory-p bn root-directory)) + (and (null bn) + (not (file-remote-p cd)) + (file-in-directory-p cd root-directory))) + collect b)) + +(defun helm-browse-project-build-buffers-source (directory) + (helm-make-source "Buffers in project" 'helm-source-buffers + :header-name (lambda (name) + (format + "%s (%s)" + name (abbreviate-file-name directory))) + :buffer-list (lambda () (helm-browse-project-get-buffers directory)))) + +(defun helm-browse-project-walk-directory (directory) + "Default function for `helm-browse-project-default-find-files-fn'." + (helm-walk-directory + directory + :directories nil :path 'full :skip-subdirs t)) + +(defun helm-browse-project-find-files-1 (directory program) + "List files in DIRECTORY recursively with external PROGRAM." + (let ((cmd (cl-ecase program + (ag "ag --hidden -g '.*' %s") + (rg "rg --files --hidden -g '*' %s")))) + (with-temp-buffer + (call-process-shell-command + (format cmd directory) + nil t nil) + (mapcar (lambda (f) (expand-file-name f directory)) + (split-string (buffer-string) "\n"))))) + +(defun helm-browse-project-ag-find-files (directory) + "A suitable function for `helm-browse-project-default-find-files-fn'. +Use AG as backend." + (helm-browse-project-find-files-1 directory 'ag)) + +(defun helm-browse-project-rg-find-files (directory) + "A suitable function for `helm-browse-project-default-find-files-fn'. +Use RG as backend." + (helm-browse-project-find-files-1 directory 'rg)) + +(defun helm-browse-project-ag (_candidate) + "helm-grep AG action for helm-browse-project." + (let ((dir (with-helm-buffer (helm-attr 'root-dir)))) + (helm-grep-ag dir helm-current-prefix-arg))) + +(defun helm-browse-project-run-ag () + "Runs helm-grep AG from helm-browse-project." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-browse-project-ag))) +(put 'helm-browse-project-run-ag 'helm-only t) + +(defclass helm-browse-project-override-inheritor (helm-type-file) ()) + +(defclass helm-browse-project-source (helm-source-in-buffer + helm-browse-project-override-inheritor) + ((root-dir :initarg :root-dir + :initform nil + :custom 'file) + (match-part :initform + (lambda (c) + (if (with-helm-buffer + helm-ff-transformer-show-only-basename) + (helm-basename c) c))) + (filter-one-by-one :initform + (lambda (c) + (if (with-helm-buffer + helm-ff-transformer-show-only-basename) + (cons (propertize (helm-basename c) + 'face 'helm-ff-file) + c) + (propertize c 'face 'helm-ff-file))))) + "Class to define a source in helm-browse-project handling non VC +handled directories.") + +(defmethod helm--setup-source :after ((source helm-browse-project-override-inheritor)) + (let ((actions (slot-value source 'action))) + (setf (slot-value source 'action) + (helm-append-at-nth + (symbol-value actions) + '(("Grep project with AG `M-g a, C-u select type'" . helm-browse-project-ag)) + 7)) + (setf (slot-value source 'keymap) helm-browse-project-map))) + +(defun helm-browse-project-find-files (directory &optional refresh) + "Browse non VC handled directory DIRECTORY." + (when refresh (remhash directory helm--browse-project-cache)) + (unless (gethash directory helm--browse-project-cache) + (puthash directory (funcall helm-browse-project-default-find-files-fn + directory) + helm--browse-project-cache)) + (helm :sources `(,(helm-browse-project-build-buffers-source directory) + ,(helm-make-source "Browse project" + 'helm-browse-project-source + :root-dir directory + :data (gethash directory helm--browse-project-cache) + :header-name + (lambda (name) + (format + "%s (%s)" + name (abbreviate-file-name directory))))) + :ff-transformer-show-only-basename nil + :buffer "*helm browse project*")) + +(defvar helm-browse-project-history nil) + +;;;###autoload +(defun helm-projects-history (arg) + (interactive "P") + (helm :sources + (helm-build-sync-source "Project history" + :candidates helm-browse-project-history + :action (lambda (candidate) + (with-helm-default-directory candidate + (helm-browse-project + (or arg helm-current-prefix-arg))))) + :buffer "*helm browse project history*")) + +;;;###autoload +(defun helm-browse-project (arg) + "Preconfigured helm to browse projects. +Browse files and see status of project with its vcs. +Only HG and GIT are supported for now. +Fall back to `helm-browse-project-find-files' +if current directory is not under control of one of those vcs. +With a prefix ARG browse files recursively, with two prefix ARG +rebuild the cache. +If the current directory is found in the cache, start +`helm-browse-project-find-files' even with no prefix ARG. +NOTE: The prefix ARG have no effect on the VCS controlled directories. + +Needed dependencies for VCS: + +and +." + (interactive "P") + (require 'helm-x-files) + (let ((helm-type-buffer-actions + (remove (assoc "Browse project from buffer" + helm-type-buffer-actions) + helm-type-buffer-actions)) + (helm-buffers-in-project-p t)) + (cl-flet ((push-to-hist (root) + (setq helm-browse-project-history + (cons root (delete root helm-browse-project-history))))) + (helm-acond ((and (require 'helm-ls-git nil t) + (fboundp 'helm-ls-git-root-dir) + (helm-ls-git-root-dir)) + (push-to-hist it) + (helm-ls-git-ls)) + ((and (require 'helm-ls-hg nil t) + (fboundp 'helm-hg-root) + (helm-hg-root)) + (push-to-hist it) + (helm-hg-find-files-in-project)) + ((helm-browse-project-get--root-dir (helm-current-directory)) + (if (or arg (gethash it helm--browse-project-cache)) + (progn + (push-to-hist it) + (helm-browse-project-find-files it (equal arg '(16)))) + (helm :sources (helm-browse-project-build-buffers-source it) + :buffer "*helm browse project*"))))))) + +(defun helm-browse-project-get--root-dir (directory) + (cl-loop with dname = (file-name-as-directory directory) + while (and dname (not (gethash dname helm--browse-project-cache))) + if (file-remote-p dname) + do (setq dname nil) else + do (setq dname (helm-basedir (substring dname 0 (1- (length dname))))) + finally return (or dname (file-name-as-directory directory)))) + +(defun helm-ff-browse-project (_candidate) + "Browse project in current directory. +See `helm-browse-project'." + (with-helm-default-directory helm-ff-default-directory + (helm-browse-project helm-current-prefix-arg))) + +(defun helm-ff-run-browse-project () + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-ff-browse-project))) +(put 'helm-ff-run-browse-project 'helm-only t) + +(defun helm-ff-gid (_candidate) + (with-helm-default-directory helm-ff-default-directory + (helm-gid))) + +(defun helm-ff-run-gid () + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-ff-gid))) +(put 'helm-ff-run-gid 'helm-only t) + +;; helm-find bindings for helm-find-files. +(defun helm-ff-find-sh-command (_candidate) + "Run `helm-find' from `helm-find-files'." + (require 'helm-find) + (helm-find-1 helm-ff-default-directory)) + +(defun helm-ff-run-find-sh-command () + "Run find shell command action with key from `helm-find-files'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-ff-find-sh-command))) +(put 'helm-ff-run-find-sh-command 'helm-only t) + + +;;;###autoload +(defun helm-find-files (arg) + "Preconfigured `helm' for helm implementation of `find-file'. +Called with a prefix arg show history if some. +Don't call it from programs, use `helm-find-files-1' instead. +This is the starting point for nearly all actions you can do on files." + (interactive "P") + (let* ((hist (and arg helm-ff-history (helm-find-files-history nil))) + (smart-input (or hist (helm-find-files-initial-input))) + (default-input (expand-file-name (helm-current-directory))) + (input (cond ((and (null hist) + helm-find-files-ignore-thing-at-point) + default-input) + ((and (eq major-mode 'org-agenda-mode) + org-directory + (not smart-input)) + (file-name-as-directory + (expand-file-name org-directory))) + ((and (eq major-mode 'dired-mode) smart-input) + (file-name-directory smart-input)) + ((and (not (string= smart-input "")) + smart-input)) + (t default-input))) + (input-as-presel (null (nth 0 (file-attributes input)))) + (presel (helm-aif (or hist + (and input-as-presel input) + (buffer-file-name (current-buffer)) + (and (eq major-mode 'dired-mode) + smart-input)) + (if (and helm-ff-transformer-show-only-basename + (null hist) + (not (string-match-p "[.]\\{1,2\\}\\'" it))) + (helm-basename it) it)))) + ;; Continue using the same display function as history which used + ;; probably itself the same display function as inner HFF call, + ;; i.e. if history was using frame use a frame otherwise use a window. + (when (and hist (buffer-live-p (get-buffer helm-ff-history-buffer-name))) + (helm-set-local-variable 'helm-display-function + (with-current-buffer helm-ff-history-buffer-name + helm-display-function) + 'helm--last-frame-parameters + (with-current-buffer helm-ff-history-buffer-name + helm--last-frame-parameters))) + (set-text-properties 0 (length input) nil input) + (setq current-prefix-arg nil) + ;; Allow next helm session to reuse helm--last-frame-parameters as + ;; resume would do. + (let ((helm--executing-helm-action (not (null hist)))) + (helm-find-files-1 input (and presel (null helm-ff-no-preselect) + (concat "^" (regexp-quote presel))))))) + +;;;###autoload +(defun helm-delete-tramp-connection () + "Allow deleting tramp connection or marked tramp connections at once. + +This replace `tramp-cleanup-connection' which is partially broken in +emacs < to 25.1.50.1 (See Emacs Bug#24432). + +It allows additionally to delete more than one connection at once." + (interactive) + (let ((helm-quit-if-no-candidate + (lambda () + (message "No Tramp connection found")))) + (helm :sources (helm-build-sync-source "Tramp connections" + :candidates (tramp-list-connections) + :candidate-transformer (lambda (candidates) + (cl-loop for v in candidates + for name = (apply #'tramp-make-tramp-file-name + (cl-loop with v = (helm-ff--tramp-cons-or-vector v) + for i across v collect i)) + when (or (processp (tramp-get-connection-process v)) + (buffer-live-p (get-buffer (tramp-buffer-name v)))) + collect (cons name v))) + :action (lambda (_vec) + (let ((vecs (helm-marked-candidates))) + (cl-loop for v in vecs + do (progn + (tramp-cleanup-connection v) + (remhash v tramp-cache-data)))))) + :buffer "*helm tramp connections*"))) + + +(provide 'helm-files) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-files.el ends here diff --git a/elpa/helm-20191031.839/helm-find.el b/elpa/helm-20191031.839/helm-find.el new file mode 100644 index 00000000..9c1ab0ca --- /dev/null +++ b/elpa/helm-20191031.839/helm-find.el @@ -0,0 +1,175 @@ +;;; helm-find.el --- helm interface for find command. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'helm-files) +(require 'helm-external) + +(defcustom helm-findutils-skip-boring-files t + "Ignore boring files in find command results." + :group 'helm-files + :type 'boolean) + +(defcustom helm-findutils-search-full-path nil + "Search in full path with shell command find when non--nil. +I.e use the -path/ipath arguments of find instead of -name/iname." + :group 'helm-files + :type 'boolean) + +(defcustom helm-find-noerrors nil + "Prevent showing error messages in helm buffer when non nil." + :group 'helm-files + :type 'boolean) + +(defvar helm-find-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-generic-files-map) + (define-key map (kbd "DEL") 'helm-delete-backward-no-update) + map)) + +(defvar helm-source-findutils + (helm-build-async-source "Find" + :header-name (lambda (name) + (concat name " in [" (helm-default-directory) "]")) + :candidates-process 'helm-find-shell-command-fn + :filtered-candidate-transformer 'helm-findutils-transformer + :action-transformer 'helm-transform-file-load-el + :persistent-action 'helm-ff-kill-or-find-buffer-fname + :action 'helm-type-file-actions + :help-message 'helm-generic-file-help-message + :keymap helm-find-map + :candidate-number-limit 9999 + :requires-pattern 3)) + +(defun helm-findutils-transformer (candidates _source) + (let (non-essential + (default-directory (helm-default-directory))) + (cl-loop for i in candidates + for abs = (expand-file-name + (helm-aif (file-remote-p default-directory) + (concat it i) i)) + for type = (car (file-attributes abs)) + for disp = (if (and helm-ff-transformer-show-only-basename + (not (string-match "[.]\\{1,2\\}$" i))) + (helm-basename abs) abs) + collect (cond ((eq t type) + (cons (propertize disp 'face 'helm-ff-directory) + abs)) + ((stringp type) + (cons (propertize disp 'face 'helm-ff-symlink) + abs)) + (t (cons (propertize disp 'face 'helm-ff-file) + abs)))))) + +(defun helm-find--build-cmd-line () + (require 'find-cmd) + (let* ((default-directory (or (file-remote-p default-directory 'localname) + default-directory)) + (patterns+options (split-string helm-pattern "\\(\\`\\| +\\)\\* +")) + (fold-case (helm-set-case-fold-search (car patterns+options))) + (patterns (split-string (car patterns+options))) + (additional-options (and (cdr patterns+options) + (list (concat (cadr patterns+options) " ")))) + (ignored-dirs ()) + (ignored-files (when helm-findutils-skip-boring-files + (cl-loop for f in completion-ignored-extensions + if (string-match "/$" f) + do (push (replace-match "" nil t f) + ignored-dirs) + else collect (concat "*" f)))) + (path-or-name (if helm-findutils-search-full-path + '(ipath path) '(iname name))) + (name-or-iname (if fold-case + (car path-or-name) (cadr path-or-name)))) + (find-cmd (and ignored-dirs + `(prune (name ,@ignored-dirs))) + (and ignored-files + `(not (name ,@ignored-files))) + `(and ,@(mapcar + (lambda (pattern) + `(,name-or-iname ,(concat "*" pattern "*"))) + patterns) + ,@additional-options)))) + +(defun helm-find-shell-command-fn () + "Asynchronously fetch candidates for `helm-find'. +Additional find options can be specified after a \"*\" +separator." + (let* (process-connection-type + non-essential + (cmd (concat (helm-find--build-cmd-line) + (if helm-find-noerrors "2> /dev/null" ""))) + (proc (start-file-process-shell-command "hfind" helm-buffer cmd))) + (helm-log "Find command:\n%s" cmd) + (prog1 proc + (set-process-sentinel + proc + (lambda (process event) + (helm-process-deferred-sentinel-hook + process event (helm-default-directory)) + (if (string= event "finished\n") + (helm-locate-update-mode-line "Find") + (helm-log "Error: Find %s" + (replace-regexp-in-string "\n" "" event)))))))) + +(defun helm-find-1 (dir) + (let ((default-directory (file-name-as-directory dir))) + (helm :sources 'helm-source-findutils + :buffer "*helm find*" + :ff-transformer-show-only-basename nil + :case-fold-search helm-file-name-case-fold-search))) + + +;;; Preconfigured commands +;; +;; +;;;###autoload +(defun helm-find (arg) + "Preconfigured `helm' for the find shell command. + +Recursively find files whose names are matched by all specified +globbing PATTERNs under the current directory using the external +program specified in `find-program' (usually \"find\"). Every +input PATTERN is silently wrapped into two stars: *PATTERN*. + +With prefix argument, prompt for a directory to search. + +When user option `helm-findutils-search-full-path' is non-nil, +match against complete paths, otherwise, against file names +without directory part. + +The (possibly empty) list of globbing PATTERNs can be followed by +the separator \"*\" plus any number of additional arguments that +are passed to \"find\" literally." + (interactive "P") + (let ((directory + (if arg + (file-name-as-directory + (read-directory-name "DefaultDirectory: ")) + default-directory))) + (helm-find-1 directory))) + +(provide 'helm-find) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-find.el ends here diff --git a/elpa/helm-20191031.839/helm-font.el b/elpa/helm-20191031.839/helm-font.el new file mode 100644 index 00000000..d0a37a4a --- /dev/null +++ b/elpa/helm-20191031.839/helm-font.el @@ -0,0 +1,335 @@ +;;; helm-font --- Font and ucs selection for Helm -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'cl-lib) +(require 'helm) +(require 'helm-help) + + +(defgroup helm-font nil + "Related applications to display fonts in helm." + :group 'helm) + +(defcustom helm-ucs-recent-size 10 + "Number of recent chars to keep." + :type 'integer + :group 'helm-font) + +(defcustom helm-ucs-actions + '(("Insert character" . helm-ucs-insert-char) + ("Insert character name" . helm-ucs-insert-name) + ("Insert character code in hex" . helm-ucs-insert-code) + ("Kill marked characters" . helm-ucs-kill-char) + ("Kill name" . helm-ucs-kill-name) + ("Kill code" . helm-ucs-kill-code)) + "Actions for `helm-source-ucs'." + :group 'helm-font + :type '(alist :key-type string :value-type function)) + +(defvar helm-ucs-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "") 'helm-ucs-persistent-delete) + (define-key map (kbd "") 'helm-ucs-persistent-backward) + (define-key map (kbd "") 'helm-ucs-persistent-forward) + (define-key map (kbd "C-c SPC") 'helm-ucs-persistent-insert-space) + map) + "Keymap for `helm-ucs'.") + +(defface helm-ucs-char + '((((class color) (background dark)) (:foreground "Gold"))) + "Face used to display ucs characters." + :group 'helm-font) + +;;; Xfont selection +;; +;; +(defvar helm-xfonts-cache nil) +(defvar helm-previous-font nil) +(defvar helm-source-xfonts + (helm-build-sync-source "X Fonts" + :init (lambda () + (unless helm-xfonts-cache + (setq helm-xfonts-cache + (x-list-fonts "*"))) + ;; Save current font so it can be restored in cleanup + (setq helm-previous-font (cdr (assq 'font (frame-parameters))))) + :candidates 'helm-xfonts-cache + :action '(("Copy font to kill ring" . (lambda (elm) + (kill-new elm))) + ("Set font" . (lambda (elm) + (kill-new elm) + (set-frame-font elm 'keep-size) + (message "Font copied to kill ring")))) + :cleanup (lambda () + ;; Restore previous font + (set-frame-font helm-previous-font 'keep-size)) + :persistent-action (lambda (new-font) + (set-frame-font new-font 'keep-size) + (kill-new new-font)) + :persistent-help "Preview font and copy to kill-ring")) + + +;;; 𝕌𝕔𝕤 𝕊𝕪𝕞𝕓𝕠𝕝 𝕔𝕠𝕞𝕡𝕝𝕖𝕥𝕚𝕠𝕟 +;; +;; +(defvar helm-ucs--max-len nil) +(defvar helm-ucs--names nil) +(defvar helm-ucs-history nil) +(defvar helm-ucs-recent nil + "Ring of recent `helm-ucs' selections.") + +(defun helm-calculate-ucs-alist-max-len (names) + "Calculate the length of the longest NAMES list candidate." + (cl-loop for (_n . v) in names + maximize (length (format "#x%x:" v)) into code + maximize (max 1 (string-width (format "%c" v))) into char + finally return (cons code char))) + +(defun helm-calculate-ucs-hash-table-max-len (names) + "Calculate the length of the longest NAMES hash table candidate." + (cl-loop for _n being the hash-keys of names + using (hash-values v) + maximize (length (format "#x%x:" v)) into code + maximize (max 1 (string-width (format "%c" v))) into char + finally return (cons code char))) + +(defun helm-calculate-ucs-max-len () + "Calculate the length of longest `ucs-names' candidate." + (let ((ucs-struct (ucs-names))) + (if (hash-table-p ucs-struct) + (helm-calculate-ucs-hash-table-max-len ucs-struct) + (helm-calculate-ucs-alist-max-len ucs-struct)))) + +(defun helm-ucs-collect-symbols-alist (names) + "Collect ucs symbols from the NAMES list." + (cl-loop with pr = (make-progress-reporter + "collecting ucs names" + 0 (length names)) + for (n . v) in names + for count from 1 + for xcode = (format "#x%x:" v) + for len = (length xcode) + for diff = (- (car helm-ucs--max-len) len) + for code = (format "(#x%x): " v) + for char = (propertize (format "%c" v) + 'face 'helm-ucs-char) + unless (or (string= "" n) + ;; `char-displayable-p' return a font object or + ;; t for some char that are displayable but have + ;; no special font (e.g 10) so filter out char + ;; with no font. + (not (fontp (char-displayable-p (read xcode))))) + collect + (concat code (make-string diff ? ) + char " " n) + and do (progress-reporter-update pr count))) + +(defun helm-ucs-collect-symbols-hash-table (names) + "Collect ucs symbols from the NAMES hash-table." + (cl-loop with pr = (make-progress-reporter + "collecting ucs names" + 0 (hash-table-count names)) + for n being the hash-keys of names + using (hash-values v) + for count from 1 + for xcode = (format "#x%x:" v) + for len = (length xcode) + for diff = (- (car helm-ucs--max-len) len) + for code = (format "(#x%x): " v) + for char = (propertize (format "%c" v) + 'face 'helm-ucs-char) + unless (or (string= "" n) + (not (fontp (char-displayable-p (read xcode))))) + collect + (concat code (make-string diff ? ) + char " " n) + and do (progress-reporter-update pr count))) + +(defun helm-ucs-collect-symbols (ucs-struct) + "Collect ucs symbols from UCS-STRUCT. + +Depending on the Emacs version, the variable `ucs-names' can +either be an alist or a hash-table." + (if (hash-table-p ucs-struct) + (helm-ucs-collect-symbols-hash-table ucs-struct) + (helm-ucs-collect-symbols-alist ucs-struct))) + +(defun helm-ucs-init () + "Initialize an helm buffer with ucs symbols. +Only math* symbols are collected." + (unless helm-ucs--max-len + (setq helm-ucs--max-len + (helm-calculate-ucs-max-len))) + (or helm-ucs--names + (setq helm-ucs--names + (helm-ucs-collect-symbols (ucs-names))))) + +;; Actions (insertion) + +(defun helm-ucs-match (candidate n) + "Return the N part of an ucs CANDIDATE. +Where N=1 is the ucs code, N=2 the ucs char and N=3 the ucs name." + (when (string-match + "^(\\(#x[a-f0-9]+\\)): *\\(.\\) *\\([^:]+\\)+" + candidate) + (match-string n candidate))) + +(defun helm-ucs-save-recentest (candidate) + (let ((lst (cons candidate (delete candidate helm-ucs-recent)))) + (setq helm-ucs-recent + (if (> (length lst) helm-ucs-recent-size) + (nbutlast lst 1) + lst)))) + +(defun helm-ucs-insert (candidate n) + "Insert the N part of CANDIDATE." + (with-helm-current-buffer + (helm-ucs-save-recentest candidate) + (insert (helm-ucs-match candidate n)))) + +(defun helm-ucs-insert-char (candidate) + "Insert ucs char part of CANDIDATE at point." + (helm-ucs-insert candidate 2)) + +(defun helm-ucs-insert-code (candidate) + "Insert ucs code part of CANDIDATE at point." + (helm-ucs-insert candidate 1)) + +(defun helm-ucs-insert-name (candidate) + "Insert ucs name part of CANDIDATE at point." + (helm-ucs-insert candidate 3)) + +;; Kill actions +(defun helm-ucs-kill-char (_candidate) + "Action that concatenate ucs marked chars." + (let ((marked (helm-marked-candidates))) + (cl-loop for candidate in marked + do (helm-ucs-save-recentest candidate)) + (kill-new (mapconcat (lambda (x) + (helm-ucs-match x 2)) + marked "")))) + +(defun helm-ucs-kill-code (candidate) + (helm-ucs-save-recentest candidate) + (kill-new (helm-ucs-match candidate 1))) + +(defun helm-ucs-kill-name (candidate) + (helm-ucs-save-recentest candidate) + (kill-new (helm-ucs-match candidate 3))) + +;; Navigation in current-buffer (persistent) + +(defun helm-ucs-forward-char (_candidate) + (with-helm-current-buffer + (forward-char 1))) + +(defun helm-ucs-backward-char (_candidate) + (with-helm-current-buffer + (forward-char -1))) + +(defun helm-ucs-delete-backward (_candidate) + (with-helm-current-buffer + (delete-char -1))) + +(defun helm-ucs-insert-space (_candidate) + (with-helm-current-buffer + (insert " "))) + +(defun helm-ucs-persistent-forward () + (interactive) + (with-helm-alive-p + (helm-attrset 'action-forward 'helm-ucs-forward-char) + (helm-execute-persistent-action 'action-forward))) +(put 'helm-ucs-persistent-forward 'helm-only t) + +(defun helm-ucs-persistent-backward () + (interactive) + (with-helm-alive-p + (helm-attrset 'action-back 'helm-ucs-backward-char) + (helm-execute-persistent-action 'action-back))) +(put 'helm-ucs-persistent-backward 'helm-only t) + +(defun helm-ucs-persistent-delete () + (interactive) + (with-helm-alive-p + (helm-attrset 'action-delete 'helm-ucs-delete-backward) + (helm-execute-persistent-action 'action-delete))) +(put 'helm-ucs-persistent-delete 'helm-only t) + +(defun helm-ucs-persistent-insert-space () + (interactive) + (with-helm-alive-p + (helm-attrset 'action-insert-space 'helm-ucs-insert-space) + (helm-execute-persistent-action 'action-insert-space))) + +(defvar helm-source-ucs-recent + (helm-build-sync-source "Recent UCS" + :action helm-ucs-actions + :candidates (lambda () helm-ucs-recent) + :help-message helm-ucs-help-message + :keymap helm-ucs-map + :volatile t)) + +(defvar helm-source-ucs + (helm-build-in-buffer-source "UCS names" + :data #'helm-ucs-init + :get-line #'buffer-substring + :help-message 'helm-ucs-help-message + :filtered-candidate-transformer + (lambda (candidates _source) (sort candidates #'helm-generic-sort-fn)) + :action helm-ucs-actions + :persistent-action (lambda (candidate) + (helm-ucs-insert-char candidate) + (helm-force-update)) + :keymap helm-ucs-map) + "Source for collecting `ucs-names' math symbols.") + +;;;###autoload +(defun helm-select-xfont () + "Preconfigured `helm' to select Xfont." + (interactive) + (helm :sources 'helm-source-xfonts + :buffer "*helm select xfont*")) + +;;;###autoload +(defun helm-ucs (arg) + "Preconfigured helm for `ucs-names'. + +Called with a prefix arg force reloading cache." + (interactive "P") + (when arg + (setq helm-ucs--names nil + helm-ucs--max-len nil + ucs-names nil)) + (let ((char (helm-aif (char-after) (string it)))) + (helm :sources (list helm-source-ucs-recent helm-source-ucs) + :history 'helm-ucs-history + :input (and char (multibyte-string-p char) char) + :buffer "*helm ucs*"))) + +(provide 'helm-font) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-font.el ends here diff --git a/elpa/helm-20191031.839/helm-for-files.el b/elpa/helm-20191031.839/helm-for-files.el new file mode 100644 index 00000000..e875c56e --- /dev/null +++ b/elpa/helm-20191031.839/helm-for-files.el @@ -0,0 +1,308 @@ +;;; helm-for-files.el --- helm-for-files and related. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'helm-files) +(require 'helm-external) +(require 'helm-bookmark) + +(defcustom helm-multi-files-toggle-locate-binding "C-c p" + "Default binding to switch back and forth locate in `helm-multi-files'." + :group 'helm-files + :type 'string) + +(defcustom helm-for-files-preferred-list + '(helm-source-buffers-list + helm-source-recentf + helm-source-bookmarks + helm-source-file-cache + helm-source-files-in-current-dir + helm-source-locate) + "Your preferred sources for `helm-for-files' and `helm-multi-files'. + +When adding a source here it is up to you to ensure the library of +this source is accessible and properly loaded." + :type '(repeat (choice symbol)) + :group 'helm-files) + +(defcustom helm-for-files-tramp-not-fancy t + "Colorize remote files when non nil. + +Be aware that a nil value will make tramp display very slow." + :group 'helm-files + :type 'boolean) + +;;; File Cache +;; +;; +(defvar file-cache-alist) + +(defclass helm-file-cache (helm-source-in-buffer helm-type-file) + ((init :initform (lambda () (require 'filecache))))) + +(defun helm-file-cache-get-candidates () + (cl-loop for item in file-cache-alist append + (cl-destructuring-bind (base &rest dirs) item + (cl-loop for dir in dirs collect + (concat dir base))))) + +(defvar helm-source-file-cache nil) + +(defcustom helm-file-cache-fuzzy-match nil + "Enable fuzzy matching in `helm-source-file-cache' when non--nil." + :group 'helm-files + :type 'boolean + :set (lambda (var val) + (set var val) + (setq helm-source-file-cache + (helm-make-source "File Cache" 'helm-file-cache + :fuzzy-match helm-file-cache-fuzzy-match + :data 'helm-file-cache-get-candidates)))) + +(cl-defun helm-file-cache-add-directory-recursively + (dir &optional match (ignore-dirs t)) + (require 'filecache) + (cl-loop for f in (helm-walk-directory + dir + :path 'full + :directories nil + :match match + :skip-subdirs ignore-dirs) + do (file-cache-add-file f))) + +(defun helm-transform-file-cache (actions _candidate) + (let ((source (helm-get-current-source))) + (if (string= (assoc-default 'name source) "File Cache") + (append actions + '(("Remove marked files from file-cache" + . helm-ff-file-cache-remove-file))) + actions))) + +;;; Recentf files +;; +;; +(defvar helm-recentf--basename-flag nil) + +(defun helm-recentf-pattern-transformer (pattern) + (let ((pattern-no-flag (replace-regexp-in-string " -b" "" pattern))) + (cond ((and (string-match " " pattern-no-flag) + (string-match " -b\\'" pattern)) + (setq helm-recentf--basename-flag t) + pattern-no-flag) + ((string-match "\\([^ ]*\\) -b\\'" pattern) + (prog1 (match-string 1 pattern) + (setq helm-recentf--basename-flag t))) + (t (setq helm-recentf--basename-flag nil) + pattern)))) + +(defcustom helm-turn-on-recentf t + "Automatically turn on `recentf-mode' when non-nil." + :group 'helm-files + :type 'boolean) + +(defclass helm-recentf-source (helm-source-sync helm-type-file) + ((init :initform (lambda () + (require 'recentf) + (when helm-turn-on-recentf (recentf-mode 1)))) + (candidates :initform (lambda () recentf-list)) + (pattern-transformer :initform 'helm-recentf-pattern-transformer) + (match-part :initform (lambda (candidate) + (if (or helm-ff-transformer-show-only-basename + helm-recentf--basename-flag) + (helm-basename candidate) candidate))) + (migemo :initform t) + (persistent-action :initform 'helm-ff-kill-or-find-buffer-fname))) + +(defmethod helm--setup-source :after ((source helm-recentf-source)) + (setf (slot-value source 'action) + (append (symbol-value (helm-actions-from-type-file)) + '(("Delete file(s) from recentf" . + (lambda (_candidate) + (cl-loop for file in (helm-marked-candidates) + do (setq recentf-list (delete file recentf-list))))))))) + +(defvar helm-source-recentf nil + "See (info \"(emacs)File Conveniences\"). +Set `recentf-max-saved-items' to a bigger value if default is too small.") + +(defcustom helm-recentf-fuzzy-match nil + "Enable fuzzy matching in `helm-source-recentf' when non--nil." + :group 'helm-files + :type 'boolean + :set (lambda (var val) + (set var val) + (let ((helm-fuzzy-sort-fn 'helm-fuzzy-matching-sort-fn-preserve-ties-order)) + (setq helm-source-recentf + (helm-make-source "Recentf" 'helm-recentf-source + :fuzzy-match helm-recentf-fuzzy-match))))) + + +;;; Files in current dir +;; +;; +(defun helm-highlight-files (files _source) + "A basic transformer for helm files sources. +Colorize only symlinks, directories and files." + (cl-loop with mp-fn = (or (assoc-default + 'match-part (helm-get-current-source)) + 'identity) + for i in files + for disp = (if (and helm-ff-transformer-show-only-basename + (not (helm-dir-is-dot i)) + (not (and helm--url-regexp + (string-match helm--url-regexp i))) + (not (string-match helm-ff-url-regexp i))) + (helm-basename i) (abbreviate-file-name i)) + for isremote = (or (file-remote-p i) + (helm-file-on-mounted-network-p i)) + ;; Call file-attributes only if: + ;; - file is not remote + ;; - helm-for-files--tramp-not-fancy is nil and file is remote AND + ;; connected. (Issue #1679) + for type = (and (or (null isremote) + (and (null helm-for-files-tramp-not-fancy) + (file-remote-p i nil t))) + (car (file-attributes i))) + collect + (cond ((and (null type) isremote) (cons disp i)) + ((stringp type) + (cons (propertize disp + 'face 'helm-ff-symlink + 'match-part (funcall mp-fn disp) + 'help-echo (expand-file-name i)) + i)) + ((eq type t) + (cons (propertize disp + 'face 'helm-ff-directory + 'match-part (funcall mp-fn disp) + 'help-echo (expand-file-name i)) + i)) + (t (cons (propertize disp + 'face 'helm-ff-file + 'match-part (funcall mp-fn disp) + 'help-echo (expand-file-name i)) + i))))) + +(defclass helm-files-in-current-dir-source (helm-source-sync helm-type-file) + ((candidates :initform (lambda () + (with-helm-current-buffer + (let ((dir (helm-current-directory))) + (when (file-accessible-directory-p dir) + (directory-files dir t)))))) + (pattern-transformer :initform 'helm-recentf-pattern-transformer) + (match-part :initform (lambda (candidate) + (if (or helm-ff-transformer-show-only-basename + helm-recentf--basename-flag) + (helm-basename candidate) candidate))) + (fuzzy-match :initform t) + (migemo :initform t))) + +(defvar helm-source-files-in-current-dir + (helm-make-source "Files from Current Directory" + 'helm-files-in-current-dir-source)) + +;;;###autoload +(defun helm-for-files () + "Preconfigured `helm' for opening files. +Run all sources defined in `helm-for-files-preferred-list'." + (interactive) + (require 'helm-x-files) + (unless helm-source-buffers-list + (setq helm-source-buffers-list + (helm-make-source "Buffers" 'helm-source-buffers))) + (helm :sources helm-for-files-preferred-list + :ff-transformer-show-only-basename nil + :buffer "*helm for files*" + :truncate-lines helm-buffers-truncate-lines)) + +(defun helm-multi-files-toggle-to-locate () + (interactive) + (with-helm-alive-p + (with-helm-buffer + (if (setq helm-multi-files--toggle-locate + (not helm-multi-files--toggle-locate)) + (progn + (helm-set-sources (unless (memq 'helm-source-locate + helm-sources) + (cons 'helm-source-locate helm-sources))) + (helm-set-source-filter '(helm-source-locate))) + (helm-kill-async-processes) + (helm-set-sources (remove 'helm-source-locate + helm-for-files-preferred-list)) + (helm-set-source-filter nil))))) +(put 'helm-multi-files-toggle-to-locate 'helm-only t) + +;;;###autoload +(defun helm-multi-files () + "Preconfigured helm like `helm-for-files' but running locate only on demand. + +Allow toggling back and forth from locate to others sources with +`helm-multi-files-toggle-locate-binding' key. +This avoid launching needlessly locate when what you search is already +found." + (interactive) + (require 'helm-x-files) + (unless helm-source-buffers-list + (setq helm-source-buffers-list + (helm-make-source "Buffers" 'helm-source-buffers))) + (setq helm-multi-files--toggle-locate nil) + (helm-locate-set-command) + (helm-set-local-variable 'helm-async-outer-limit-hook + (list (lambda () + (when (and helm-locate-fuzzy-match + (not (string-match-p + "\\s-" helm-pattern))) + (helm-redisplay-buffer))))) + (let ((sources (remove 'helm-source-locate helm-for-files-preferred-list)) + (helm-locate-command + (if helm-locate-fuzzy-match + (unless (string-match-p "\\`locate -b" helm-locate-command) + (replace-regexp-in-string + "\\`locate" "locate -b" helm-locate-command)) + helm-locate-command)) + (old-key (lookup-key + helm-map + (read-kbd-macro helm-multi-files-toggle-locate-binding)))) + (with-helm-temp-hook 'helm-after-initialize-hook + (define-key helm-map (kbd helm-multi-files-toggle-locate-binding) + 'helm-multi-files-toggle-to-locate)) + (unwind-protect + (helm :sources sources + :ff-transformer-show-only-basename nil + :buffer "*helm multi files*" + :truncate-lines helm-buffers-truncate-lines) + (define-key helm-map (kbd helm-multi-files-toggle-locate-binding) + old-key)))) + +;;;###autoload +(defun helm-recentf () + "Preconfigured `helm' for `recentf'." + (interactive) + (helm :sources 'helm-source-recentf + :ff-transformer-show-only-basename nil + :buffer "*helm recentf*")) + +(provide 'helm-for-files) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-for-files.el ends here diff --git a/elpa/helm-20191031.839/helm-grep.el b/elpa/helm-20191031.839/helm-grep.el new file mode 100644 index 00000000..43b491e3 --- /dev/null +++ b/elpa/helm-20191031.839/helm-grep.el @@ -0,0 +1,1661 @@ +;;; helm-grep.el --- Helm Incremental Grep. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: +(require 'cl-lib) +(require 'format-spec) +(require 'helm) +(require 'helm-help) +(require 'helm-regexp) + +;;; load wgrep proxy if it's available +(require 'wgrep-helm nil t) + +(declare-function helm-buffer-list "helm-buffers") +(declare-function View-quit "view") +(declare-function doc-view-goto-page "doc-view" (page)) +(declare-function pdf-view-goto-page "pdf-view" (page &optional window)) +(declare-function helm-mm-split-pattern "helm-multi-match") +(declare-function helm--ansi-color-apply "helm-lib") +(defvar helm--ansi-color-regexp) + + +(defgroup helm-grep nil + "Grep related Applications and libraries for Helm." + :group 'helm) + +(defcustom helm-grep-default-command + "grep --color=always -a -d skip %e -n%cH -e %p %f" + "Default grep format command for `helm-do-grep-1'. +Where: +'%e' format spec is for --exclude or --include grep options or + ack-grep --type option. (Not mandatory) + +'%c' format spec is for case-fold-search, + whether to use the -i option of grep. (Not mandatory) + When you specify this spec, helm grep will use smartcase + that is when a upcase character is found in pattern case will + be respected and no '-i' option will be used, otherwise, when + no upcase character is found in pattern always use '-i'. + If you don't want this behavior, don't use this spec and + specify or not the '-i' option. + Note that with ack-grep this is not needed, just specify + the '--smart-case' option. + +'%p' format spec is for pattern. (Mandatory) + +'%f' format spec is for filenames. (Mandatory) + +If your grep version doesn't support the --exclude/include args +don't specify the '%e' format spec. + +Helm also support ack-grep and git-grep , +here a default command example for ack-grep: + +\(setq helm-grep-default-command \"ack-grep -Hn --color --smart-case --no-group %e %p %f\" + helm-grep-default-recurse-command \"ack-grep -H --color --smart-case --no-group %e %p %f\") + +You can ommit the %e spec if you don't want to be prompted for types. + +NOTE: Helm for ack-grep support ANSI sequences, so you can remove +the \"--no-color\" option safely (recommended) +However you should specify --color to enable multi matches highlighting +because ack disable it when output is piped. + +Same for grep you can use safely the option \"--color=always\" (default). +You can customize the color of matches using GREP_COLORS env var. +e.g: \(setenv \"GREP_COLORS\" \"ms=30;43:mc=30;43:sl=01;37:cx=:fn=35:ln=32:bn=32:se=36\") + +To enable ANSI color in git-grep just add \"--color=always\". +To customize the ANSI color in git-grep, GREP_COLORS have no effect, +you will have to setup this in your .gitconfig: + + [color \"grep\"] + match = black yellow + +where \"black\" is the foreground and \"yellow\" the background. +See the git documentation for more infos. + +`helm-grep-default-command' and `helm-grep-default-recurse-command'are +independents, so you can enable `helm-grep-default-command' with ack-grep +and `helm-grep-default-recurse-command' with grep if you want to be faster +on recursive grep. + +NOTE: Remote grepping is not available with ack-grep, + and badly supported with grep because tramp handle badly + repeated remote processes in a short delay (< to 5s)." + :group 'helm-grep + :type 'string) + +(defcustom helm-grep-default-recurse-command + "grep --color=always -a -d recurse %e -n%cH -e %p %f" + "Default recursive grep format command for `helm-do-grep-1'. +See `helm-grep-default-command' for format specs and infos about ack-grep." + :group 'helm-grep + :type 'string) + +(defcustom helm-default-zgrep-command + "zgrep --color=always -a -n%cH -e %p %f" + "Default command for Zgrep. +See `helm-grep-default-command' for infos on format specs. +Option --color=always is supported and can be used safely +to replace the helm internal match highlighting, +see `helm-grep-default-command' for more infos." + :group 'helm-grep + :type 'string) + +(defcustom helm-pdfgrep-default-command + "pdfgrep --color always -niH %s %s" + "Default command for pdfgrep. +Option \"--color always\" is supported starting helm version 1.7.8, +when used matchs will be highlighted according to GREP_COLORS env var." + :group 'helm-grep + :type 'string) + +(defcustom helm-pdfgrep-default-recurse-command + "pdfgrep --color always -rniH %s %s" + "Default recurse command for pdfgrep. +Option \"--color always\" is supported starting helm version 1.7.8, +when used matchs will be highlighted according to GREP_COLORS env var." + :group 'helm-grep + :type 'string) + +(defcustom helm-pdfgrep-default-read-command nil + "Default command to read pdf files from pdfgrep. +Where '%f' format spec is filename and '%p' is page number. +e.g In Ubuntu you can set it to: + + \"evince --page-label=%p '%f'\" + +If set to nil either `doc-view-mode' or `pdf-view-mode' will be used +instead of an external command." + :group 'helm-grep + :type 'string) + +(defcustom helm-grep-max-length-history 100 + "Max number of elements to save in `helm-grep-history'." + :group 'helm-grep + :type 'integer) + +(defcustom helm-zgrep-file-extension-regexp + ".*\\(\\.gz\\|\\.bz\\|\\.xz\\|\\.lzma\\)$" + "Default file extensions zgrep will search in." + :group 'helm-grep + :type 'string) + +(defcustom helm-grep-preferred-ext nil + "This file extension will be preselected for grep." + :group 'helm-grep + :type 'string) + +(defcustom helm-grep-save-buffer-name-no-confirm nil + "when *hgrep* already exists,auto append suffix." + :group 'helm-grep + :type 'boolean) + +(defcustom helm-grep-ignored-files + (cons ".#*" (delq nil (mapcar (lambda (s) + (unless (string-match-p "/\\'" s) + (concat "*" s))) + completion-ignored-extensions))) + "List of file names which `helm-grep' shall exclude." + :group 'helm-grep + :type '(repeat string)) + +(defcustom helm-grep-ignored-directories + helm-walk-ignore-directories + "List of names of sub-directories which `helm-grep' shall not recurse into." + :group 'helm-grep + :type '(repeat string)) + +(defcustom helm-grep-truncate-lines t + "When nil the grep line that appears will not be truncated." + :group 'helm-grep + :type 'boolean) + +(defcustom helm-grep-file-path-style 'basename + "File path display style when grep results are displayed. +Possible value are: + basename: displays only the filename, none of the directory path + absolute: displays absolute path + relative: displays relative path from root grep directory." + :group 'helm-grep + :type '(choice (const :tag "Basename" basename) + (const :tag "Absolute" absolute) + (const :tag "Relative" relative))) + +(defcustom helm-grep-actions + (helm-make-actions + "Find File" 'helm-grep-action + "Find file other frame" 'helm-grep-other-frame + "Save results in grep buffer" 'helm-grep-save-results + "Find file other window (C-u vertically)" 'helm-grep-other-window) + "Actions for helm grep." + :group 'helm-grep + :type '(alist :key-type string :value-type function)) + +(defcustom helm-grep-pipe-cmd-switches nil + "A list of additional parameters to pass to grep pipe command. +This will be used for pipe command for multiple pattern matching +for grep, zgrep ack-grep and git-grep backends. +If you add extra args for ack-grep, use ack-grep options, +for others (grep, zgrep and git-grep) use grep options. +Here are the commands where you may want to add switches: + + grep --color=always + ack-grep --smart-case --color + +You probably don't need to use this unless you know what you are doing." + :group 'helm-grep + :type '(repeat string)) + +(defcustom helm-grep-ag-pipe-cmd-switches nil + "A list of additional parameters to pass to grep-ag pipe command. +Use parameters compatibles with the backend you are using +\(i.e AG for AG, PT for PT or RG for RG) + +You probably don't need to use this unless you know what you are doing." + :group 'helm-grep + :type '(repeat string)) + +(defcustom helm-grep-input-idle-delay 0.6 + "Same as `helm-input-idle-delay' but for grep commands. +It have a higher value than `helm-input-idle-delay' to avoid +flickering when updating." + :group 'helm-grep + :type 'float) + +;;; Faces +;; +;; +(defgroup helm-grep-faces nil + "Customize the appearance of helm-grep." + :prefix "helm-" + :group 'helm-grep + :group 'helm-faces) + +(defface helm-grep-match + '((((background light)) :foreground "#b00000") + (((background dark)) :foreground "gold1")) + "Face used to highlight grep matches. +Have no effect when grep backend use \"--color=\"." + :group 'helm-grep-faces) + +(defface helm-grep-file + '((t (:foreground "BlueViolet" + :underline t))) + "Face used to highlight grep results filenames." + :group 'helm-grep-faces) + +(defface helm-grep-lineno + '((t (:foreground "Darkorange1"))) + "Face used to highlight grep number lines." + :group 'helm-grep-faces) + +(defface helm-grep-finish + '((t (:foreground "Green"))) + "Face used in mode line when grep is finish." + :group 'helm-grep-faces) + +(defface helm-grep-cmd-line + '((t (:inherit font-lock-type-face))) + "Face used to highlight grep command line when no results." + :group 'helm-grep-faces) + + +;;; Keymaps +;; +;; +(defvar helm-grep-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "M-") 'helm-goto-next-file) + (define-key map (kbd "M-") 'helm-goto-precedent-file) + (define-key map (kbd "C-c o") 'helm-grep-run-other-window-action) + (define-key map (kbd "C-c C-o") 'helm-grep-run-other-frame-action) + (define-key map (kbd "C-x C-s") 'helm-grep-run-save-buffer) + (define-key map (kbd "DEL") 'helm-delete-backward-no-update) + map) + "Keymap used in Grep sources.") + +(defcustom helm-grep-use-ioccur-style-keys t + "Use Arrow keys to jump to occurences. +Note that if you define this variable with `setq' your change will +have no effect, use customize instead." + :group 'helm-grep + :type 'boolean + :set (lambda (var val) + (set var val) + (if val + (progn + (define-key helm-grep-map (kbd "") 'helm-execute-persistent-action) + (define-key helm-grep-map (kbd "") 'helm-grep-run-default-action)) + (define-key helm-grep-map (kbd "") nil) + (define-key helm-grep-map (kbd "") nil)))) + +(defvar helm-pdfgrep-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "M-") 'helm-goto-next-file) + (define-key map (kbd "M-") 'helm-goto-precedent-file) + (define-key map (kbd "DEL") 'helm-delete-backward-no-update) + map) + "Keymap used in pdfgrep.") + +(defvar helm-grep-mode-map + (let ((map (make-sparse-keymap))) + (define-key map (kbd "RET") 'helm-grep-mode-jump) + (define-key map (kbd "C-o") 'helm-grep-mode-jump-other-window) + (define-key map (kbd "") 'helm-grep-mode-jump-other-window-forward) + (define-key map (kbd "") 'helm-grep-mode-jump-other-window-backward) + (define-key map (kbd "") 'helm-gm-next-file) + (define-key map (kbd "") 'helm-gm-precedent-file) + (define-key map (kbd "M-n") 'helm-grep-mode-jump-other-window-forward) + (define-key map (kbd "M-p") 'helm-grep-mode-jump-other-window-backward) + (define-key map (kbd "M-N") 'helm-gm-next-file) + (define-key map (kbd "M-P") 'helm-gm-precedent-file) + map)) + + +;;; Internals vars +;; +;; +(defvar helm-rzgrep-cache (make-hash-table :test 'equal)) +(defvar helm-grep-default-function 'helm-grep-init) +(defvar helm-zgrep-recurse-flag nil) +(defvar helm-grep-history nil) +(defvar helm-grep-ag-history nil) +(defvar helm-grep-last-targets nil) +(defvar helm-grep-include-files nil) +(defvar helm-grep-in-recurse nil) +(defvar helm-grep-use-zgrep nil) +(defvar helm-grep-default-directory-fn nil + "A function that should return a directory to expand candidate to. +It is intended to use as a let-bound variable, DON'T set this globaly.") +(defvar helm-pdfgrep-targets nil) +(defvar helm-grep-last-cmd-line nil) +(defvar helm-grep-split-line-regexp "^\\([[:lower:][:upper:]]?:?.*?\\):\\([0-9]+\\):\\(.*\\)") + + +;;; Init +;; +;; +(defun helm-grep-prepare-candidates (candidates in-directory) + "Prepare filenames and directories CANDIDATES for grep command line." + ;; If one or more candidate is a directory, search in all files + ;; of this candidate (e.g /home/user/directory/*). + ;; If r option is enabled search also in subdidrectories. + ;; We need here to expand wildcards to support crap windows filenames + ;; as grep doesn't accept quoted wildcards (e.g "dir/*.el"). + (if helm-zgrep-recurse-flag + (mapconcat 'shell-quote-argument candidates " ") + ;; When candidate is a directory, search in all its files. + ;; NOTE that `file-expand-wildcards' will return also + ;; directories, they will be ignored by grep but not + ;; by ack-grep that will grep all files of this directory + ;; without recursing in their subdirs though, see that as a one + ;; level recursion with ack-grep. + ;; So I leave it as it is, considering it is a feature. [1] + (cl-loop for i in candidates append + (cond ((string-match "^git" helm-grep-default-command) + (list i)) + ;; Candidate is a directory and we use recursion or ack. + ((and (file-directory-p i) + (or helm-grep-in-recurse + ;; ack-grep accept directory [1]. + (helm-grep-use-ack-p))) + (list (expand-file-name i))) + ;; Grep doesn't support directory only when not in recurse. + ((file-directory-p i) + (file-expand-wildcards + (concat (file-name-as-directory (expand-file-name i)) "*") t)) + ;; Candidate is a file or wildcard and we use recursion, use the + ;; current directory instead of candidate. + ((and (or (file-exists-p i) (string-match "[*]" i)) + helm-grep-in-recurse) + (list (expand-file-name + (directory-file-name ; Needed for windoze. + (file-name-directory (directory-file-name i)))))) + ;; Else should be one or more file/directory + ;; possibly marked. + ;; When real is a normal filename without wildcard + ;; file-expand-wildcards returns a list of one file. + ;; wildcards should have been already handled by + ;; helm-read-file-name or helm-find-files but do it from + ;; here too in case we are called from elsewhere. + (t (file-expand-wildcards i t))) into all-files ; [1] + finally return + (let ((files (if (file-remote-p in-directory) + ;; Grep don't understand tramp filenames + ;; use the local name. + (mapcar (lambda (x) + (file-remote-p x 'localname)) + all-files) + all-files))) + ;; When user mark files and use recursion with grep + ;; backend enabled, the loop collect on each marked + ;; candidate its `file-name-directory' and we endup with + ;; duplicates (Issue #1714). FIXME: For now as a quick fix + ;; I just remove dups here but I should handle this inside + ;; the cond above. + (setq files (helm-fast-remove-dups files :test 'equal)) + (if (string-match "^git" helm-grep-default-command) + (mapconcat 'identity files " ") + (mapconcat 'shell-quote-argument files " ")))))) + +(defun helm-grep-command (&optional recursive grep) + (let* ((com (if recursive + helm-grep-default-recurse-command + helm-grep-default-command)) + (exe (if grep + (symbol-name grep) + (and com (car (split-string com " ")))))) + (if (and exe (string= exe "git")) "git-grep" exe))) + +(cl-defun helm-grep-use-ack-p (&key where) + (let* ((rec-com (helm-grep-command t)) + (norm-com (helm-grep-command)) + (norm-com-ack-p (string-match "\\`ack" norm-com)) + (rec-com-ack-p (and rec-com (string-match "\\`ack" rec-com)))) + (cl-case where + (default (and norm-com norm-com-ack-p)) + (recursive (and rec-com rec-com-ack-p)) + (strict (and norm-com rec-com rec-com-ack-p norm-com-ack-p)) + (t (and (not (and norm-com (string= norm-com "git-grep"))) + (or (and norm-com norm-com-ack-p) + (and rec-com rec-com-ack-p))))))) + +(defun helm-grep--pipe-command-for-grep-command (smartcase pipe-switches &optional grep-cmd) + (pcase (or grep-cmd (helm-grep-command)) + ;; Use grep for GNU regexp based tools. + ((or "grep" "zgrep" "git-grep") + (format "grep --color=always%s %s" + (if smartcase " -i" "") + pipe-switches)) + ;; Use ack-grep for PCRE based tools. + ;; Sometimes ack-grep cmd is ack only. + ((and (pred (string-match-p "ack")) ack) + (format "%s --smart-case --color %s" ack pipe-switches)))) + +(defun helm-grep--prepare-cmd-line (only-files &optional include zgrep) + (let* ((default-directory (or helm-ff-default-directory + (helm-default-directory) + default-directory)) + (fnargs (helm-grep-prepare-candidates + only-files default-directory)) + (ignored-files (unless (helm-grep-use-ack-p) + (mapconcat + (lambda (x) + (concat "--exclude=" + (shell-quote-argument x))) + helm-grep-ignored-files " "))) + (ignored-dirs (unless (helm-grep-use-ack-p) + (mapconcat + ;; Need grep version >=2.5.4 + ;; of Gnuwin32 on windoze. + (lambda (x) + (concat "--exclude-dir=" + (shell-quote-argument x))) + helm-grep-ignored-directories " "))) + (exclude (unless (helm-grep-use-ack-p) + (if helm-grep-in-recurse + (concat (or include ignored-files) + " " ignored-dirs) + ignored-files))) + (types (and (helm-grep-use-ack-p) + ;; When %e format spec is not specified + ;; in `helm-grep-default-command' + ;; we need to pass an empty string + ;; to types to avoid error. + (or include ""))) + (smartcase (if (helm-grep-use-ack-p) + "" + (unless (let ((case-fold-search nil)) + (string-match-p + "[[:upper:]]" helm-pattern)) + "i"))) + (helm-grep-default-command + (concat helm-grep-default-command " %m")) ; `%m' like multi. + (patterns (helm-mm-split-pattern helm-pattern t)) + (pipe-switches (mapconcat 'identity helm-grep-pipe-cmd-switches " ")) + (pipes + (helm-aif (cdr patterns) + (cl-loop with pipcom = (helm-grep--pipe-command-for-grep-command + smartcase pipe-switches) + for p in it concat + (format " | %s %s" pipcom (shell-quote-argument p))) + ""))) + (format-spec + helm-grep-default-command + (delq nil + (list (unless zgrep + (if types + (cons ?e types) + (cons ?e exclude))) + (cons ?c (or smartcase "")) + (cons ?p (shell-quote-argument (car patterns))) + (cons ?f fnargs) + (cons ?m pipes)))))) + +(defun helm-grep-init (cmd-line) + "Start an asynchronous grep process with CMD-LINE using ZGREP if non--nil." + (let* ((default-directory (or helm-ff-default-directory + (helm-default-directory) + default-directory)) + (zgrep (string-match "\\`zgrep" cmd-line)) + ;; Use pipe only with grep, zgrep or git-grep. + (process-connection-type (and (not zgrep) (helm-grep-use-ack-p))) + (tramp-verbose helm-tramp-verbose) + (start-time (float-time)) + (proc-name (if helm-grep-use-zgrep + "Zgrep" + (capitalize + (if helm-grep-in-recurse + (helm-grep-command t) + (helm-grep-command))))) + non-essential) + ;; Start grep process. + (helm-log "Starting Grep process in directory `%s'" default-directory) + (helm-log "Command line used was:\n\n%s" + (concat ">>> " (propertize cmd-line 'face 'helm-grep-cmd-line) "\n\n")) + (prog1 ; This function should return the process first. + (start-file-process-shell-command + proc-name helm-buffer cmd-line) + ;; Init sentinel. + (set-process-sentinel + (get-buffer-process helm-buffer) + (lambda (process event) + (let* ((err (process-exit-status process)) + (noresult (= err 1))) + (unless (and err (> err 0)) + (helm-process-deferred-sentinel-hook + process event (helm-default-directory))) + (cond ((and noresult + ;; This is a workaround for zgrep + ;; that exit with code 1 + ;; after a certain amount of results. + (with-helm-buffer (helm-empty-buffer-p))) + (with-helm-buffer + (insert (concat "* Exit with code 1, no result found," + " command line was:\n\n " + (propertize helm-grep-last-cmd-line + 'face 'helm-grep-cmd-line))) + (setq mode-line-format + `(" " mode-line-buffer-identification " " + (:eval (format "L%s" (helm-candidate-number-at-point))) " " + (:eval (propertize + (format + "[%s process finished - (no results)] " + ,proc-name) + 'face 'helm-grep-finish)))))) + ((or (string= event "finished\n") + (and noresult + ;; This is a workaround for zgrep + ;; that exit with code 1 + ;; after a certain amount of results. + (with-helm-buffer (not (helm-empty-buffer-p))))) + (helm-log "%s process finished with %s results in %fs" + proc-name + (helm-get-candidate-number) + (- (float-time) start-time)) + (helm-maybe-show-help-echo) + (with-helm-window + (setq mode-line-format + `(" " mode-line-buffer-identification " " + (:eval (format "L%s" (helm-candidate-number-at-point))) " " + (:eval (propertize + (format + "[%s process finished in %.2fs - (%s results)] " + ,proc-name + ,(- (float-time) start-time) + (helm-get-candidate-number)) + 'face 'helm-grep-finish)))) + (force-mode-line-update) + (when (and helm-allow-mouse helm-selection-point) + (helm--bind-mouse-for-selection helm-selection-point)))) + ;; Catch error output in log. + (t (helm-log + "Error: %s %s" + proc-name + (replace-regexp-in-string "\n" "" event)))))))))) + +(defun helm-grep-collect-candidates () + (let ((cmd-line (helm-grep--prepare-cmd-line + helm-grep-last-targets + helm-grep-include-files + helm-grep-use-zgrep))) + (set (make-local-variable 'helm-grep-last-cmd-line) cmd-line) + (funcall helm-grep-default-function cmd-line))) + + +;;; Actions +;; +;; +(defun helm-grep-action (candidate &optional where) + "Define a default action for `helm-do-grep-1' on CANDIDATE. +WHERE can be one of other-window, other-frame." + (let* ((split (helm-grep-split-line candidate)) + (split-pat (helm-mm-split-pattern helm-input)) + (lineno (string-to-number (nth 1 split))) + (loc-fname (or (with-current-buffer + (if (eq major-mode 'helm-grep-mode) + (current-buffer) + helm-buffer) + (get-text-property (point-at-bol) 'helm-grep-fname)) + (car split))) + (tramp-method (file-remote-p (or helm-ff-default-directory + default-directory) 'method)) + (tramp-host (file-remote-p (or helm-ff-default-directory + default-directory) 'host)) + (tramp-prefix (concat "/" tramp-method ":" tramp-host ":")) + (fname (if tramp-host + (concat tramp-prefix loc-fname) loc-fname))) + (cl-case where + (other-window (helm-window-show-buffers + (list (find-file-noselect fname)) t)) + (other-frame (find-file-other-frame fname)) + (grep (helm-grep-save-results-1)) + (pdf (if helm-pdfgrep-default-read-command + (helm-pdfgrep-action-1 split lineno (car split)) + (find-file (car split)) (if (derived-mode-p 'pdf-view-mode) + (pdf-view-goto-page lineno) + (doc-view-goto-page lineno)))) + (t (find-file fname))) + (unless (or (eq where 'grep) (eq where 'pdf)) + (helm-goto-line lineno)) + ;; Move point to the nearest matching regexp from bol. + (cl-loop for reg in split-pat + when (save-excursion + (condition-case _err + (if helm-migemo-mode + (helm-mm-migemo-forward reg (point-at-eol) t) + (re-search-forward reg (point-at-eol) t)) + (invalid-regexp nil))) + collect (match-beginning 0) into pos-ls + finally (when pos-ls (goto-char (apply #'min pos-ls)))) + ;; Save history + (unless (or helm-in-persistent-action + (eq major-mode 'helm-grep-mode) + (string= helm-pattern "")) + (setq helm-grep-history + (cons helm-pattern + (delete helm-pattern helm-grep-history))) + (when (> (length helm-grep-history) + helm-grep-max-length-history) + (setq helm-grep-history + (delete (car (last helm-grep-history)) + helm-grep-history)))))) + +(defun helm-grep-persistent-action (candidate) + "Persistent action for `helm-do-grep-1'. +With a prefix arg record CANDIDATE in `mark-ring'." + (helm-grep-action candidate) + (helm-highlight-current-line)) + +(defun helm-grep-other-window (candidate) + "Jump to result in other window from helm grep." + (helm-grep-action candidate 'other-window)) + +(defun helm-grep-other-frame (candidate) + "Jump to result in other frame from helm grep." + (helm-grep-action candidate 'other-frame)) + +(defun helm-goto-next-or-prec-file (n) + "Go to next or precedent candidate file in helm grep/etags buffers. +If N is positive go forward otherwise go backward." + (let* ((allow-mode (or (eq major-mode 'helm-grep-mode) + (eq major-mode 'helm-moccur-mode) + (eq major-mode 'helm-occur-mode))) + (sel (if allow-mode + (buffer-substring (point-at-bol) (point-at-eol)) + (helm-get-selection nil t))) + (current-line-list (helm-grep-split-line sel)) + (current-fname (nth 0 current-line-list)) + (bob-or-eof (if (eq n 1) 'eobp 'bobp)) + (mark-maybe (lambda () + (if allow-mode + (ignore) + (helm-mark-current-line))))) + (catch 'break + (while (not (funcall bob-or-eof)) + (forward-line n) ; Go forward or backward depending of n value. + ;; Exit when current-fname is not matched or in `helm-grep-mode' + ;; the line is not a grep line i.e 'fname:num:tag'. + (setq sel (buffer-substring (point-at-bol) (point-at-eol))) + (when helm-allow-mouse + (helm--mouse-reset-selection-help-echo)) + (unless (or (string= current-fname + (car (helm-grep-split-line sel))) + (and (eq major-mode 'helm-grep-mode) + (not (get-text-property (point-at-bol) 'helm-grep-fname)))) + (funcall mark-maybe) + (throw 'break nil)))) + (cond ((and (> n 0) (eobp)) + (re-search-backward ".") + (forward-line 0) + (funcall mark-maybe)) + ((and (< n 0) (bobp)) + (helm-aif (next-single-property-change (point-at-bol) 'helm-grep-fname) + (goto-char it) + (forward-line 1)) + (funcall mark-maybe))) + (unless allow-mode + (helm-follow-execute-persistent-action-maybe) + (helm-log-run-hook 'helm-move-selection-after-hook)))) + +;;;###autoload +(defun helm-goto-precedent-file () + "Go to precedent file in helm grep/etags buffers." + (interactive) + (with-helm-alive-p + (with-helm-window + (helm-goto-next-or-prec-file -1)))) +(put 'helm-goto-precedent-file 'helm-only t) + +;;;###autoload +(defun helm-goto-next-file () + "Go to precedent file in helm grep/etags buffers." + (interactive) + (with-helm-window + (helm-goto-next-or-prec-file 1))) + +(defun helm-grep-run-default-action () + "Run grep default action from `helm-do-grep-1'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-grep-action))) +(put 'helm-grep-run-default-action 'helm-only t) + +(defun helm-grep-run-other-window-action () + "Run grep goto other window action from `helm-do-grep-1'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-grep-other-window))) +(put 'helm-grep-run-other-window-action 'helm-only t) + +(defun helm-grep-run-other-frame-action () + "Run grep goto other frame action from `helm-do-grep-1'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-grep-other-frame))) +(put 'helm-grep-run-other-frame-action 'helm-only t) + +(defun helm-grep-run-save-buffer () + "Run grep save results action from `helm-do-grep-1'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-grep-save-results))) +(put 'helm-grep-run-save-buffer 'helm-only t) + + +;;; helm-grep-mode +;; +;; +(defun helm-grep-save-results (candidate) + (helm-grep-action candidate 'grep)) + +(defun helm-grep-save-results-1 () + "Save helm grep result in a `helm-grep-mode' buffer." + (let ((buf "*hgrep*") + new-buf + (pattern (with-helm-buffer helm-input-local)) + (src-name (assoc-default 'name (helm-get-current-source)))) + (when (get-buffer buf) + (if helm-grep-save-buffer-name-no-confirm + (setq new-buf (format "*hgrep|%s|-%s" pattern + (format-time-string "%H-%M-%S*"))) + (setq new-buf (helm-read-string "GrepBufferName: " buf)) + (cl-loop for b in (helm-buffer-list) + when (and (string= new-buf b) + (not (y-or-n-p + (format "Buffer `%s' already exists overwrite? " + new-buf)))) + do (setq new-buf (helm-read-string "GrepBufferName: " "*hgrep ")))) + (setq buf new-buf)) + (with-current-buffer (get-buffer-create buf) + (setq default-directory (or helm-ff-default-directory + (helm-default-directory) + default-directory)) + (setq buffer-read-only t) + (let ((inhibit-read-only t) + (map (make-sparse-keymap))) + (erase-buffer) + (insert "-*- mode: helm-grep -*-\n\n" + (format "%s Results for `%s':\n\n" src-name pattern)) + (save-excursion + (insert (with-current-buffer helm-buffer + (goto-char (point-min)) (forward-line 1) + (buffer-substring (point) (point-max))))) + (save-excursion + (while (not (eobp)) + (add-text-properties (point-at-bol) (point-at-eol) + `(keymap ,map + help-echo ,(concat + (get-text-property + (point) 'helm-grep-fname) + "\nmouse-1: set point\nmouse-2: jump to selection") + mouse-face highlight)) + (define-key map [mouse-1] 'mouse-set-point) + (define-key map [mouse-2] 'helm-grep-mode-mouse-jump) + (define-key map [mouse-3] 'ignore) + (forward-line 1)))) + (helm-grep-mode)) + (pop-to-buffer buf) + (message "Helm %s Results saved in `%s' buffer" src-name buf))) + +(defun helm-grep-mode-mouse-jump (event) + (interactive "e") + (let* ((window (posn-window (event-end event))) + (pos (posn-point (event-end event)))) + (with-selected-window window + (when (eq major-mode 'helm-grep-mode) + (goto-char pos) + (helm-grep-mode-jump))))) +(put 'helm-grep-mode-mouse-jump 'helm-only t) + +(define-derived-mode helm-grep-mode + special-mode "helm-grep" + "Major mode to provide actions in helm grep saved buffer. + +Special commands: +\\{helm-grep-mode-map}" + (set (make-local-variable 'helm-grep-last-cmd-line) + (with-helm-buffer helm-grep-last-cmd-line)) + (set (make-local-variable 'revert-buffer-function) + #'helm-grep-mode--revert-buffer-function)) +(put 'helm-grep-mode 'helm-only t) + +(defun helm-grep-mode--revert-buffer-function (&optional _ignore-auto _noconfirm) + (goto-char (point-min)) + (when (re-search-forward helm-grep-split-line-regexp nil t) (forward-line 0)) + (let ((inhibit-read-only t)) + (delete-region (point) (point-max))) + (message "Reverting buffer...") + (let ((process-connection-type + ;; Git needs a nil value otherwise it tries to use a pager. + (null (string-match-p "\\`git" helm-grep-last-cmd-line)))) + (set-process-sentinel + (start-file-process-shell-command + "hgrep" (generate-new-buffer "*hgrep revert*") helm-grep-last-cmd-line) + 'helm-grep-mode--sentinel))) + +(defun helm-grep-mode--sentinel (process event) + (when (string= event "finished\n") + (with-current-buffer (current-buffer) + (let ((inhibit-read-only t)) + (save-excursion + (cl-loop for l in (with-current-buffer (process-buffer process) + (prog1 (split-string (buffer-string) "\n") + (kill-buffer))) + for line = (if (string-match-p helm--ansi-color-regexp l) + (helm--ansi-color-apply l) l) + when (string-match helm-grep-split-line-regexp line) + do (insert (propertize + (car (helm-grep-filter-one-by-one line)) + ;; needed for wgrep. + 'helm-realvalue line) + "\n")))) + (when (fboundp 'wgrep-cleanup-overlays) + (wgrep-cleanup-overlays (point-min) (point-max))) + (message "Reverting buffer done")))) + +(defun helm-gm-next-file () + (interactive) + (helm-goto-next-or-prec-file 1)) + +(defun helm-gm-precedent-file () + (interactive) + (helm-goto-next-or-prec-file -1)) + +(defun helm-grep-mode-jump () + (interactive) + (helm-grep-action + (buffer-substring (point-at-bol) (point-at-eol))) + (helm-match-line-cleanup-pulse)) + +(defun helm-grep-mode-jump-other-window-1 (arg) + (condition-case nil + (progn + (when (or (eq last-command 'helm-grep-mode-jump-other-window-forward) + (eq last-command 'helm-grep-mode-jump-other-window-backward)) + (forward-line arg)) + (save-selected-window + (helm-grep-action (buffer-substring (point-at-bol) (point-at-eol)) + 'other-window) + (helm-match-line-cleanup-pulse) + (recenter))) + (error nil))) + +(defun helm-grep-mode-jump-other-window-forward (arg) + (interactive "p") + (helm-grep-mode-jump-other-window-1 arg)) + +(defun helm-grep-mode-jump-other-window-backward (arg) + (interactive "p") + (helm-grep-mode-jump-other-window-1 (- arg))) + +(defun helm-grep-mode-jump-other-window () + (interactive) + (let ((candidate (buffer-substring (point-at-bol) (point-at-eol)))) + (condition-case nil + (progn (helm-grep-action candidate 'other-window) + (helm-match-line-cleanup-pulse)) + (error nil)))) + + +;;; ack-grep types +;; +;; +(defun helm-grep-hack-types () + "Return a list of known ack-grep types." + (with-temp-buffer + ;; "--help-types" works with both 1.96 and 2.1+, while + ;; "--help types" works only with 1.96 Issue #422. + ;; `helm-grep-command' should return the ack executable + ;; when this function is used in the right context + ;; i.e After checking is we are using ack-grep with + ;; `helm-grep-use-ack-p'. + (call-process (helm-grep-command t) nil t nil "--help-types") + (goto-char (point-min)) + (cl-loop while (re-search-forward + "^ *--\\(\\[no\\]\\)\\([^. ]+\\) *\\(.*\\)" nil t) + collect (cons (concat (match-string 2) + " [" (match-string 3) "]") + (match-string 2)) + collect (cons (concat "no" (match-string 2) + " [" (match-string 3) "]") + (concat "no" (match-string 2)))))) + +(defun helm-grep-ack-types-transformer (candidates _source) + (cl-loop for i in candidates + if (stringp i) + collect (rassoc i helm-grep-ack-types-cache) + else + collect i)) + +(defvar helm-grep-ack-types-cache nil) +(defun helm-grep-read-ack-type () + "Select types for the '--type' argument of ack-grep." + (require 'helm-mode) + (require 'helm-adaptive) + (setq helm-grep-ack-types-cache (helm-grep-hack-types)) + (let ((types (helm-comp-read + "Types: " helm-grep-ack-types-cache + :name "*Ack-grep types*" + :marked-candidates t + :must-match t + :fc-transformer '(helm-adaptive-sort + helm-grep-ack-types-transformer) + :buffer "*helm ack-types*"))) + (mapconcat (lambda (type) (concat "--type=" type)) types " "))) + + +;;; grep extensions +;; +;; +(defun helm-grep-guess-extensions (files) + "Try to guess file extensions in FILES list when using grep recurse. +These extensions will be added to command line with --include arg of grep." + (cl-loop with ext-list = (list helm-grep-preferred-ext "*") + with lst = (if (file-directory-p (car files)) + (directory-files + (car files) nil + directory-files-no-dot-files-regexp) + files) + for i in lst + for ext = (file-name-extension i 'dot) + for glob = (and ext (not (string= ext "")) + (concat "*" ext)) + unless (or (not glob) + (and glob-list (member glob glob-list)) + (and glob-list (member glob ext-list)) + (and glob-list (member glob helm-grep-ignored-files))) + collect glob into glob-list + finally return (delq nil (append ext-list glob-list)))) + +(defun helm-grep-get-file-extensions (files) + "Try to return a list of file extensions to pass to '--include' arg of grep." + (require 'helm-adaptive) + (let* ((all-exts (helm-grep-guess-extensions + (mapcar 'expand-file-name files))) + (extensions (helm-comp-read "Search Only in: " all-exts + :marked-candidates t + :fc-transformer 'helm-adaptive-sort + :buffer "*helm grep exts*" + :name "*helm grep extensions*"))) + (when (listp extensions) ; Otherwise it is empty string returned by C-RET. + ;; If extensions is a list of one string containing spaces, + ;; assume user entered more than one glob separated by space(s) and + ;; split this string to pass it later to mapconcat. + ;; e.g '("*.el *.py") + (cl-loop for i in extensions + append (split-string-and-unquote i " "))))) + + +;;; Set up source +;; +;; +(defvar helm-grep-before-init-hook nil + "Hook that runs before initialization of the helm buffer.") + +(defvar helm-grep-after-init-hook nil + "Hook that runs after initialization of the helm buffer.") + +(defclass helm-grep-class (helm-source-async) + ((candidates-process :initform 'helm-grep-collect-candidates) + (filter-one-by-one :initform 'helm-grep-filter-one-by-one) + (keymap :initform helm-grep-map) + (pcre :initarg :pcre :initform nil + :documentation + " Backend is using pcre regexp engine when non--nil.") + (nohighlight :initform t) + (nomark :initform t) + (backend :initarg :backend + :initform nil + :documentation + " The grep backend that will be used. + It is actually used only as an internal flag + and don't set the backend by itself. + You probably don't want to modify this.") + (candidate-number-limit :initform 9999) + (help-message :initform 'helm-grep-help-message) + (history :initform 'helm-grep-history) + (action :initform 'helm-grep-actions) + (persistent-action :initform 'helm-grep-persistent-action) + (persistent-help :initform "Jump to line (`C-u' Record in mark ring)") + (requires-pattern :initform 2) + (before-init-hook :initform 'helm-grep-before-init-hook) + (after-init-hook :initform 'helm-grep-after-init-hook) + (group :initform 'helm-grep))) + +(defvar helm-source-grep nil) + +(defmethod helm--setup-source ((source helm-grep-class)) + (call-next-method) + (helm-aif (and helm-follow-mode-persistent + (if (eq (slot-value source 'backend) 'git) + helm-source-grep-git + helm-source-grep)) + (setf (slot-value source 'follow) + (assoc-default 'follow it)))) + +(cl-defun helm-do-grep-1 (targets &optional recurse backend exts + default-input input (source 'helm-source-grep)) + "Launch helm using backend BACKEND on a list of TARGETS files. + +When RECURSE is given and BACKEND is 'grep' use -r option of +BACKEND and prompt user for EXTS to set the --include args of BACKEND. +Interactively you can give more than one arg separated by space at prompt. +e.g + $Pattern: *.el *.py *.tex + +From lisp use the EXTS argument as a list of extensions as above. +If you are using ack-grep, you will be prompted for --type +instead and EXTS will be ignored. +If prompt is empty `helm-grep-ignored-files' are added to --exclude. + +Argument DEFAULT-INPUT is use as `default' arg of `helm' and INPUT +is used as `input' arg of `helm', See `helm' docstring. + +Arg BACKEND when non--nil specify which backend to use +It is used actually to specify 'zgrep' or 'git'. +When BACKEND 'zgrep' is used don't prompt for a choice +in recurse, and ignore EXTS, search being made recursively on files matching +`helm-zgrep-file-extension-regexp' only." + (let* (non-essential + (ack-rec-p (helm-grep-use-ack-p :where 'recursive)) + (exts (and recurse + ;; [FIXME] I could handle this from helm-walk-directory. + (not (eq backend 'zgrep)) ; zgrep doesn't handle -r opt. + (not ack-rec-p) + (or exts (helm-grep-get-file-extensions targets)))) + (include-files + (and exts + (mapconcat (lambda (x) + (concat "--include=" + (shell-quote-argument x))) + (if (> (length exts) 1) + (remove "*" exts) + exts) " "))) + (types (and (not include-files) + (not (eq backend 'zgrep)) + recurse + ack-rec-p + ;; When %e format spec is not specified + ;; ignore types and do not prompt for choice. + (string-match "%e" helm-grep-default-command) + (helm-grep-read-ack-type))) + (src-name (capitalize (helm-grep-command recurse backend))) + (com (cond ((eq backend 'zgrep) helm-default-zgrep-command) + ((eq backend 'git) helm-grep-git-grep-command) + (recurse helm-grep-default-recurse-command) + ;; When resuming, the local value of + ;; `helm-grep-default-command' is used, only git-grep + ;; should need this. + (t helm-grep-default-command)))) + ;; When called as action from an other source e.g *-find-files + ;; we have to kill action buffer. + (when (get-buffer helm-action-buffer) + (kill-buffer helm-action-buffer)) + ;; If `helm-find-files' haven't already started, + ;; give a default value to `helm-ff-default-directory' + ;; and set locally `default-directory' to this value . See below [1]. + (unless helm-ff-default-directory + (setq helm-ff-default-directory default-directory)) + ;; We need to store these vars locally + ;; to pass infos later to `helm-resume'. + (helm-set-local-variable + 'helm-zgrep-recurse-flag (and recurse (eq backend 'zgrep)) + 'helm-grep-last-targets targets + 'helm-grep-include-files (or include-files types) + 'helm-grep-in-recurse recurse + 'helm-grep-use-zgrep (eq backend 'zgrep) + 'helm-grep-default-command com + 'helm-input-idle-delay helm-grep-input-idle-delay + 'default-directory helm-ff-default-directory) ;; [1] + ;; Setup the source. + (set source (helm-make-source src-name 'helm-grep-class + :backend backend + :pcre (string-match-p "\\`ack" com))) + (helm + :sources source + :buffer (format "*helm %s*" (helm-grep-command recurse backend)) + :default default-input + :input input + :keymap helm-grep-map + :history 'helm-grep-history + :truncate-lines helm-grep-truncate-lines))) + + +;;; zgrep +;; +;; +(defun helm-ff-zgrep-1 (flist recursive) + (unwind-protect + (let* ((def-dir (or helm-ff-default-directory + default-directory)) + (only (if recursive + (or (gethash def-dir helm-rzgrep-cache) + (puthash + def-dir + (helm-walk-directory + def-dir + :directories nil + :path 'full + :match helm-zgrep-file-extension-regexp) + helm-rzgrep-cache)) + flist))) + (helm-do-grep-1 only recursive 'zgrep)) + (setq helm-zgrep-recurse-flag nil))) + + +;;; transformers +;; +;; +(defun helm-grep-split-line (line) + "Split a grep output line." + ;; The output of grep may send a truncated line in this chunk, + ;; so don't split until grep line is valid, that is + ;; once the second part of the line comes with next chunk + ;; send by process. + (when (string-match helm-grep-split-line-regexp line) + ;; Don't use split-string because buffer/file name or string + ;; may contain a ":". + (cl-loop for n from 1 to 3 collect (match-string n line)))) + +(defun helm-grep--filter-candidate-1 (candidate &optional dir) + (let* ((root (or dir (and helm-grep-default-directory-fn + (funcall helm-grep-default-directory-fn)))) + (ansi-p (string-match-p helm--ansi-color-regexp candidate)) + (line (if ansi-p (helm--ansi-color-apply candidate) candidate)) + (split (helm-grep-split-line line)) + (fname (if (and root split) + ;; Filename should always be provided as a local + ;; path, if the root directory is remote, the + ;; tramp prefix will be added before executing + ;; action, see `helm-grep-action' and issue #2032. + (expand-file-name (car split) + (or (file-remote-p root 'localname) + root)) + (car-safe split))) + (lineno (nth 1 split)) + (str (nth 2 split)) + (display-fname (cl-ecase helm-grep-file-path-style + (basename (and fname (file-name-nondirectory fname))) + (absolute fname) + (relative (and fname root + (file-relative-name fname root)))))) + (if (and display-fname lineno str) + (cons (concat (propertize display-fname + 'face 'helm-grep-file + 'help-echo (abbreviate-file-name fname) + 'helm-grep-fname fname) + ":" + (propertize lineno 'face 'helm-grep-lineno) + ":" + (if ansi-p str (helm-grep-highlight-match str t))) + line) + ""))) + +(defun helm-grep-filter-one-by-one (candidate) + "`filter-one-by-one' transformer function for `helm-do-grep-1'." + (let ((helm-grep-default-directory-fn + (or helm-grep-default-directory-fn + (lambda () (or helm-ff-default-directory + (and (null (eq major-mode 'helm-grep-mode)) + (helm-default-directory)) + default-directory))))) + (if (consp candidate) + ;; Already computed do nothing (default as input). + candidate + (and (stringp candidate) + (helm-grep--filter-candidate-1 candidate))))) + +(defun helm-grep-highlight-match (str &optional multi-match) + "Highlight in string STR all occurences matching `helm-pattern'." + (let (beg end) + (condition-case-unless-debug nil + (with-temp-buffer + (insert (propertize str 'read-only nil)) ; Fix (#1176) + (goto-char (point-min)) + (cl-loop for reg in + (if multi-match + ;; (m)occur. + (cl-loop for r in (helm-mm-split-pattern + helm-pattern) + unless (string-match "\\`!" r) + collect + (helm-aif (and helm-migemo-mode + (assoc r helm-mm--previous-migemo-info)) + (cdr it) r)) + ;; async sources (grep, gid etc...) + (list helm-input)) + do + (while (and (re-search-forward reg nil t) + (> (- (setq end (match-end 0)) + (setq beg (match-beginning 0))) 0)) + (helm-add-face-text-properties beg end 'helm-grep-match)) + do (goto-char (point-min))) + (buffer-string)) + (error nil)))) + + +;;; Grep from buffer list +;; +;; +(defun helm-grep-buffers-1 (candidate &optional zgrep) + "Run grep on all file--buffers or CANDIDATE if it is a file--buffer. +If one of selected buffers is not a file--buffer, +it is ignored and grep will run on all others file--buffers. +If only one candidate is selected and it is not a file--buffer, +switch to this buffer and run `helm-occur'. +If a prefix arg is given run grep on all buffers ignoring non--file-buffers." + (let* ((prefarg (or current-prefix-arg helm-current-prefix-arg)) + (helm-ff-default-directory + (if (and helm-ff-default-directory + (file-remote-p helm-ff-default-directory)) + default-directory + helm-ff-default-directory)) + (cands (if prefarg + (buffer-list) + (helm-marked-candidates))) + (win-conf (current-window-configuration)) + ;; Non--fname and remote buffers are ignored. + (bufs (cl-loop for buf in cands + for fname = (buffer-file-name (get-buffer buf)) + when (and fname (not (file-remote-p fname))) + collect (expand-file-name fname)))) + (if bufs + (if zgrep + (helm-do-grep-1 bufs nil 'zgrep) + (helm-do-grep-1 bufs)) + ;; bufs is empty, thats mean we have only CANDIDATE + ;; and it is not a buffer-filename, fallback to occur. + (switch-to-buffer candidate) + (when (get-buffer helm-action-buffer) + (kill-buffer helm-action-buffer)) + (helm-occur) + (when (eq helm-exit-status 1) + (set-window-configuration win-conf))))) + +(defun helm-grep-buffers (candidate) + "Action to grep buffers." + (helm-grep-buffers-1 candidate)) + +(defun helm-zgrep-buffers (candidate) + "Action to zgrep buffers." + (helm-grep-buffers-1 candidate 'zgrep)) + + +;;; Helm interface for pdfgrep +;; pdfgrep program +;; and a pdf-reader (e.g xpdf) are needed. +;; +(defvar helm-pdfgrep-default-function 'helm-pdfgrep-init) +(defun helm-pdfgrep-init (only-files &optional recurse) + "Start an asynchronous pdfgrep process in ONLY-FILES list." + (let* ((default-directory (or helm-ff-default-directory + default-directory)) + (fnargs (helm-grep-prepare-candidates + (if (file-remote-p default-directory) + (mapcar (lambda (x) + (file-remote-p x 'localname)) + only-files) + only-files) + default-directory)) + (cmd-line (format (if recurse + helm-pdfgrep-default-recurse-command + helm-pdfgrep-default-command) + helm-pattern + fnargs)) + process-connection-type) + ;; Start pdf grep process. + (helm-log "Starting Pdf Grep process in directory `%s'" default-directory) + (helm-log "Command line used was:\n\n%s" + (concat ">>> " (propertize cmd-line 'face 'helm-grep-cmd-line) "\n\n")) + (prog1 + (start-file-process-shell-command + "pdfgrep" helm-buffer cmd-line) + (message nil) + (set-process-sentinel + (get-buffer-process helm-buffer) + (lambda (_process event) + (if (string= event "finished\n") + (with-helm-window + (setq mode-line-format + '(" " mode-line-buffer-identification " " + (:eval (format "L%s" (helm-candidate-number-at-point))) " " + (:eval (propertize + (format "[Pdfgrep Process Finish - %s result(s)] " + (max (1- (count-lines + (point-min) (point-max))) 0)) + 'face 'helm-grep-finish)))) + (force-mode-line-update) + (when helm-allow-mouse + (helm--bind-mouse-for-selection helm-selection-point))) + (helm-log "Error: Pdf grep %s" + (replace-regexp-in-string "\n" "" event)))))))) + +(defun helm-do-pdfgrep-1 (only &optional recurse) + "Launch pdfgrep with a list of ONLY files." + (unless (executable-find "pdfgrep") + (error "Error: No such program `pdfgrep'.")) + (let (helm-grep-in-recurse) ; recursion is implemented differently in *pdfgrep. + ;; When called as action from an other source e.g *-find-files + ;; we have to kill action buffer. + (when (get-buffer helm-action-buffer) + (kill-buffer helm-action-buffer)) + (setq helm-pdfgrep-targets only) + (helm + :sources (helm-build-async-source "PdfGrep" + :init (lambda () + ;; If `helm-find-files' haven't already started, + ;; give a default value to `helm-ff-default-directory'. + (setq helm-ff-default-directory (or helm-ff-default-directory + default-directory))) + :candidates-process (lambda () + (funcall helm-pdfgrep-default-function + helm-pdfgrep-targets recurse)) + :nohighlight t + :nomark t + :filter-one-by-one #'helm-grep-filter-one-by-one + :candidate-number-limit 9999 + :history 'helm-grep-history + :keymap helm-pdfgrep-map + :help-message 'helm-pdfgrep-help-message + :action #'helm-pdfgrep-action + :persistent-help "Jump to PDF Page" + :requires-pattern 2) + :buffer "*helm pdfgrep*" + :history 'helm-grep-history))) + +(defun helm-pdfgrep-action (candidate) + (helm-grep-action candidate 'pdf)) + +(defun helm-pdfgrep-action-1 (_split pageno fname) + (save-selected-window + (start-file-process-shell-command + "pdf-reader" nil + (format-spec helm-pdfgrep-default-read-command + (list (cons ?f fname) (cons ?p pageno)))))) + +;;; AG - PT - RG +;; +;; https://github.com/ggreer/the_silver_searcher +;; https://github.com/monochromegane/the_platinum_searcher +;; https://github.com/BurntSushi/ripgrep + +(defcustom helm-grep-ag-command + "ag --line-numbers -S --hidden --color --nogroup %s %s %s" + "The default command for AG, PT or RG. + +Takes three format specs, the first for type(s), the second for pattern +and the third for directory. + +You can use safely \"--color\" (used by default) with AG RG and PT. + +For ripgrep here is the command line to use: + + rg --color=always --smart-case --no-heading --line-number %s %s %s + +NOTE: Old versions of ripgrep was not supporting colors in emacs and a +workaround had to be used (i.e prefixing command line with +\"TERM=eterm-color\"), this is no more needed. +See issue for more infos. + +You must use an output format that fit with helm grep, that is: + + \"filename:line-number:string\" + +The option \"--nogroup\" allow this. +The option \"--line-numbers\" is also mandatory except with PT (not supported). +For RG the options \"--no-heading\" and \"--line-number\" are the ones to use. + +When modifying the default colors of matches with e.g \"--color-match\" option of AG +you may want to modify as well `helm-grep-ag-pipe-cmd-switches' to have all matches +colorized with same color in multi match." + :group 'helm-grep + :type 'string) + +(defun helm-grep--ag-command () + (car (helm-remove-if-match + "\\`[A-Z]*=" (split-string helm-grep-ag-command)))) + +(defun helm-grep-ag-get-types () + "Returns a list of AG types if available with AG version. +See AG option \"--list-file-types\" +Ripgrep (rg) types are also supported if this backend is used." + (with-temp-buffer + (let* ((com (helm-grep--ag-command)) + (ripgrep (string= com "rg")) + (regex (if ripgrep "^\\(.*\\):" "^ *\\(--[a-z]*\\)")) + (prefix (if ripgrep "-t " ""))) + (when (equal (call-process com + nil t nil + (if ripgrep + "--type-list" "--list-file-types")) 0) + (goto-char (point-min)) + (cl-loop while (re-search-forward regex nil t) + for type = (match-string 1) + collect (cons type (concat prefix type))))))) + +(defun helm-grep-ag-prepare-cmd-line (pattern directory &optional type) + "Prepare AG command line to search PATTERN in DIRECTORY. +When TYPE is specified it is one of what returns `helm-grep-ag-get-types' +if available with current AG version." + (let* ((patterns (helm-mm-split-pattern pattern t)) + (pipe-switches (mapconcat 'identity helm-grep-ag-pipe-cmd-switches " ")) + (pipe-cmd (helm-acase (helm-grep--ag-command) + (("ag" "pt") + (format "%s -S --color%s" it (concat " " pipe-switches))) + ("rg" (format "rg -N -S --color=always%s" + (concat " " pipe-switches))))) + (cmd (format helm-grep-ag-command + (mapconcat 'identity type " ") + (shell-quote-argument (car patterns)) + (shell-quote-argument directory)))) + (helm-aif (cdr patterns) + (concat cmd (cl-loop for p in it concat + (format " | %s %s" + pipe-cmd (shell-quote-argument p)))) + cmd))) + +(defun helm-grep-ag-init (directory &optional type) + "Start AG process in DIRECTORY maybe searching only files of type TYPE." + (let ((default-directory (or helm-ff-default-directory + (helm-default-directory) + default-directory)) + (cmd-line (helm-grep-ag-prepare-cmd-line + helm-pattern (or (file-remote-p directory 'localname) + directory) + type)) + (start-time (float-time)) + (proc-name (helm-grep--ag-command))) + (set (make-local-variable 'helm-grep-last-cmd-line) cmd-line) + (helm-log "Starting %s process in directory `%s'" + proc-name directory) + (helm-log "Command line used was:\n\n%s" + (concat ">>> " cmd-line "\n\n")) + (prog1 + (start-file-process-shell-command + proc-name helm-buffer cmd-line) + (set-process-sentinel + (get-buffer-process helm-buffer) + (lambda (process event) + (let* ((err (process-exit-status process)) + (noresult (= err 1))) + (cond (noresult + (with-helm-buffer + (insert (concat "* Exit with code 1, no result found," + " command line was:\n\n " + (propertize helm-grep-last-cmd-line + 'face 'helm-grep-cmd-line))) + (setq mode-line-format + `(" " mode-line-buffer-identification " " + (:eval (format "L%s" (helm-candidate-number-at-point))) " " + (:eval (propertize + (format + "[%s process finished - (no results)] " + ,(upcase proc-name)) + 'face 'helm-grep-finish)))))) + ((string= event "finished\n") + (helm-log "%s process finished with %s results in %fs" + proc-name + (helm-get-candidate-number) + (- (float-time) start-time)) + (helm-maybe-show-help-echo) + (with-helm-window + (setq mode-line-format + `(" " mode-line-buffer-identification " " + (:eval (format "L%s" (helm-candidate-number-at-point))) " " + (:eval (propertize + (format + "[%s process finished in %.2fs - (%s results)] " + ,(upcase proc-name) + ,(- (float-time) start-time) + (helm-get-candidate-number)) + 'face 'helm-grep-finish)))) + (force-mode-line-update) + (when helm-allow-mouse + (helm--bind-mouse-for-selection helm-selection-point)))) + (t (helm-log + "Error: %s %s" + proc-name + (replace-regexp-in-string "\n" "" event)))))))))) + +(defclass helm-grep-ag-class (helm-source-async) + ((nohighlight :initform t) + (pcre :initarg :pcre :initform t + :documentation + " Backend is using pcre regexp engine when non--nil.") + (keymap :initform helm-grep-map) + (history :initform 'helm-grep-ag-history) + (help-message :initform 'helm-grep-help-message) + (filter-one-by-one :initform 'helm-grep-filter-one-by-one) + (persistent-action :initform 'helm-grep-persistent-action) + (persistent-help :initform "Jump to line (`C-u' Record in mark ring)") + (candidate-number-limit :initform 99999) + (requires-pattern :initform 2) + (nomark :initform t) + (action :initform 'helm-grep-actions) + (group :initform 'helm-grep))) + +(defvar helm-source-grep-ag nil) + +(defmethod helm--setup-source ((source helm-grep-ag-class)) + (call-next-method) + (helm-aif (and helm-follow-mode-persistent + helm-source-grep-ag + (assoc-default 'follow helm-source-grep-ag)) + (setf (slot-value source 'follow) it))) + +(defun helm-grep-ag-1 (directory &optional type) + "Start helm ag in DIRECTORY maybe searching in files of type TYPE." + (setq helm-source-grep-ag + (helm-make-source (upcase (helm-grep--ag-command)) 'helm-grep-ag-class + :header-name (lambda (name) + (format "%s [%s]" + name (abbreviate-file-name directory))) + :candidates-process + (lambda () (helm-grep-ag-init directory type)))) + (helm-set-local-variable 'helm-input-idle-delay helm-grep-input-idle-delay) + (helm :sources 'helm-source-grep-ag + :keymap helm-grep-map + :history 'helm-grep-ag-history + :truncate-lines helm-grep-truncate-lines + :buffer (format "*helm %s*" (helm-grep--ag-command)))) + +(defun helm-grep-ag (directory with-types) + "Start grep AG in DIRECTORY. +When WITH-TYPES is non-nil provide completion on AG types." + (require 'helm-adaptive) + (helm-grep-ag-1 directory + (helm-aif (and with-types + (helm-grep-ag-get-types)) + (helm-comp-read + "Ag type: " it + :must-match t + :marked-candidates t + :fc-transformer 'helm-adaptive-sort + :buffer "*helm ag types*")))) + +;;; Git grep +;; +;; +(defvar helm-source-grep-git nil) + +(defcustom helm-grep-git-grep-command + "git --no-pager grep -n%cH --color=always --full-name -e %p -- %f" + "The git grep default command line. +The option \"--color=always\" can be used safely. +The color of matched items can be customized in your .gitconfig +See `helm-grep-default-command' for more infos. + +The \"--exclude-standard\" and \"--no-index\" switches allow +skipping unwanted files specified in ~/.gitignore_global +and searching files not already staged (not enabled by default). + +You have also to enable this in global \".gitconfig\" with + \"git config --global core.excludesfile ~/.gitignore_global\"." + :group 'helm-grep + :type 'string) + +(defun helm-grep-git-1 (directory &optional all default input) + "Run git-grep on DIRECTORY. +If DIRECTORY is not inside or part of a git repo exit with error. +If optional arg ALL is non-nil grep the whole repo otherwise start +at DIRECTORY. +Arg DEFAULT is what you will have with `next-history-element', +arg INPUT is what you will have by default at prompt on startup." + (require 'vc) + (let* (helm-grep-default-recurse-command + ;; Expand filename of each candidate with the git root dir. + ;; The filename will be in the helm-grep-fname prop. + (helm-grep-default-directory-fn (lambda () + (vc-find-root directory ".git"))) + (helm-ff-default-directory (funcall helm-grep-default-directory-fn))) + (cl-assert helm-ff-default-directory nil "Not inside a Git repository") + (helm-do-grep-1 (if all '("") `(,(expand-file-name directory))) + nil 'git nil default input 'helm-source-grep-git))) + + +;;;###autoload +(defun helm-do-grep-ag (arg) + "Preconfigured helm for grepping with AG in `default-directory'. +With prefix-arg prompt for type if available with your AG version." + (interactive "P") + (require 'helm-files) + (helm-grep-ag (expand-file-name default-directory) arg)) + +;;;###autoload +(defun helm-grep-do-git-grep (arg) + "Preconfigured helm for git-grepping `default-directory'. +With a prefix arg ARG git-grep the whole repository." + (interactive "P") + (require 'helm-files) + (helm-grep-git-1 default-directory arg)) + + +(provide 'helm-grep) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-grep.el ends here diff --git a/elpa/helm-20191031.839/helm-help.el b/elpa/helm-20191031.839/helm-help.el new file mode 100644 index 00000000..f86ae90e --- /dev/null +++ b/elpa/helm-20191031.839/helm-help.el @@ -0,0 +1,1821 @@ +;;; helm-help.el --- Help messages for Helm. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: +(require 'helm) + + +(defgroup helm-help nil + "Embedded help for `helm'." + :group 'helm) + +(defface helm-helper + '((t :inherit helm-header)) + "Face for Helm help string in minibuffer." + :group 'helm-help) + +(defvar helm-help--string-list '(helm-help-message + helm-buffer-help-message + helm-ff-help-message + helm-read-file-name-help-message + helm-generic-file-help-message + helm-grep-help-message + helm-pdfgrep-help-message + helm-etags-help-message + helm-ucs-help-message + helm-bookmark-help-message + helm-esh-help-message + helm-buffers-ido-virtual-help-message + helm-moccur-help-message + helm-top-help-message + helm-el-package-help-message + helm-M-x-help-message + helm-imenu-help-message + helm-colors-help-message + helm-semantic-help-message + helm-kmacro-help-message)) + +(defvar helm-documentation-buffer-name "*helm documentation*") + +;;;###autoload +(defun helm-documentation () + "Preconfigured Helm for Helm documentation. +With a prefix arg refresh the documentation. + +Find here the documentation of all documented sources." + (interactive) + (let ((buf (get-buffer-create helm-documentation-buffer-name))) + (switch-to-buffer buf) + (set-buffer buf) + (let ((inhibit-read-only t)) + (erase-buffer) + (cl-loop for elm in helm-help--string-list + for str = (helm-interpret-value elm) + do (insert (substitute-command-keys str) "\n\n")) + (org-mode)) + (setq buffer-read-only t) + (view-mode))) + + +;;; Local help messages. + +;;; `helm-buffer-list' help +;; +;; +(defvar helm-buffer-help-message + "* Helm Buffer + +** Tips + +*** Completion + +**** Major-mode + +You can enter a partial major-mode name (e.g. lisp, sh) to narrow down buffers. +To specify the major-mode, prefix it with \"*\" e.g. \"*lisp\". + +If you want to match all buffers but the ones with a specific major-mode +\(negation), prefix the major-mode with \"!\" e.g. \"*!lisp\". + +If you want to specify more than one major-mode, separate them with \",\", +e.g. \"*!lisp,!sh,!fun\" lists all buffers but the ones in lisp-mode, sh-mode +and fundamental-mode. + +Then enter a space followed by a pattern to narrow down to buffers matching this +pattern. + +**** Search inside buffers + +If you enter a space and a pattern prefixed by \"@\", Helm searches for text +matching this pattern \*inside* the buffer (i.e. not in the name of the buffer). + +If you enter a pattern prefixed with an escaped \"@\", Helm searches for a +buffer matching \"@pattern\" but does not search inside. + +**** Search by directory name + +If you prefix the pattern with \"/\", Helm matches over the directory names +of the buffers. + +This feature can be used to narrow down the search to one directory while +subsequent strings entered after a space match over the buffer name only. + +Note that negation is not supported for matching on buffer filename. + +Starting from Helm v1.6.8, you can specify more than one directory. + +**** Fuzzy matching + +`helm-buffers-fuzzy-matching' turns on fuzzy matching on buffer names, but not +on directory names or major modes. A pattern starting with \"^\" disables fuzzy +matching and matches by exact regexp. + +**** Examples + +With the following pattern + + \"*lisp ^helm @moc\" + +Helm narrows down the list by selecting only the buffers that are in lisp mode, +start with \"helm\" and which content matches \"moc\". + +Without the \"@\" + + \"*lisp ^helm moc\" + +Helm looks for lisp mode buffers starting with \"helm\" and containing \"moc\" +in their name. + +With this other pattern + + \"*!lisp !helm\" + +Helm narrows down to buffers that are not in \"lisp\" mode and that do not match +\"helm\". + +With this last pattern + + /helm/ w3 + +Helm narrows down to buffers that are in any \"helm\" subdirectory and +matching \"w3\". + +*** Creating buffers + +When creating a new buffer, use `\\[universal-argument]' to choose a mode from a +list. This list is customizable, see `helm-buffers-favorite-modes'. + +*** Killing buffers + +You can kill buffers either one by one or all the marked buffers at once. + +One kill-buffer command leaves Helm while the other is persistent. Run the +persistent kill-buffer command either with the regular +`helm-execute-persistent-action' called with a prefix argument (`\\[universal-argument] \\\\[helm-execute-persistent-action]') +or with its specific command `helm-buffer-run-kill-persistent'. See the +bindings below. + +*** Switching to buffers + +To switch to a buffer, press RET, to switch to a buffer in another window, select this buffer +and press \\\\[helm-buffer-switch-other-window], when called with a prefix arg +the buffer will be displayed vertically in other window. +If you mark more than one buffer, the marked buffers will be displayed in different windows. + +*** Saving buffers + +If buffer is associated to a file and is modified, it is by default colorized in orange, +see [[Meaning of colors and prefixes for buffers][Meaning of colors and prefixes for buffers]]. +You can save these buffers with \\\\[helm-buffer-save-persistent]. +If you want to save all these buffers, you can mark them with \\[helm-buffers-mark-similar-buffers] +and save them with \\[helm-buffer-save-persistent], you can also do this in one step with +\\[helm-buffer-run-save-some-buffers], note that you will not be asked for confirmation. + +*** Meaning of colors and prefixes for buffers + +Remote buffers are prefixed with '@'. +Red => Buffer's file was modified on disk by an external process. +Indianred2 => Buffer exists but its file has been deleted. +Orange => Buffer is modified and not saved to disk. +Italic => A non-file buffer. +Yellow => Tramp archive buffer. + +** Commands +\\ +\\[helm-buffer-run-zgrep]\t\tGrep Buffer(s) works as zgrep too (`\\[universal-argument]' to grep all buffers but non-file buffers). +\\[helm-buffers-run-multi-occur]\t\tMulti-Occur buffer or marked buffers (`\\[universal-argument]' to toggle force-searching current-buffer). +\\[helm-buffer-switch-other-window]\t\tSwitch to other window. +\\[helm-buffer-switch-other-frame]\t\tSwitch to other frame. +\\[helm-buffers-run-browse-project]\t\tBrowse project from buffer. +\\[helm-buffer-run-query-replace-regexp]\t\tQuery-replace-regexp in marked buffers. +\\[helm-buffer-run-query-replace]\t\tQuery-replace in marked buffers. +\\[helm-buffer-run-ediff]\t\tEdiff current buffer with candidate. With two marked buffers, ediff those buffers. +\\[helm-buffer-run-ediff-merge]\t\tEdiff-merge current buffer with candidate. With two marked buffers, ediff-merge those buffers. +\\[helm-buffer-diff-persistent]\t\tToggle Diff-buffer with saved file without leaving Helm. +\\[helm-buffer-revert-persistent]\t\tRevert buffer without leaving Helm. +\\[helm-buffer-save-persistent]\t\tSave buffer without leaving Helm. +\\[helm-buffer-run-save-some-buffers]\t\tSave all unsaved buffers. +\\[helm-buffer-run-kill-buffers]\t\tDelete marked buffers and leave Helm. +\\[helm-buffer-run-kill-persistent]\t\tDelete buffer without leaving Helm. +\\[helm-buffer-run-rename-buffer]\t\tRename buffer. +\\[helm-toggle-all-marks]\t\tToggle all marks. +\\[helm-mark-all]\t\tMark all. +\\[helm-toggle-buffers-details]\t\tToggle details. +\\[helm-buffers-toggle-show-hidden-buffers]\t\tShow hidden buffers. +\\[helm-buffers-mark-similar-buffers]\t\tMark all buffers of the same type (color) as current buffer.") + +;;; Find files help (`helm-find-files') +;; +;; +(defvar helm-ff-help-message + "* Helm Find Files + +** Tips + +*** Navigation summary + +For a better experience you can enable auto completion by setting +`helm-ff-auto-update-initial-value' to non-nil in your init file. It is not +enabled by default to not confuse new users. + +**** Navigate with arrow keys + +You can use and arrows to go down or up one level, to enable +this customize `helm-ff-lynx-style-map'. +This is disabled by default. +Note that using `setq' will NOT work. + +**** Use `\\\\[helm-execute-persistent-action]' (persistent action) on a directory to go down one level + +On a symlinked directory a prefix argument expands to its true name. + +**** Use `\\\\[helm-find-files-up-one-level]' or `DEL' on a directory to go up one level + +***** `DEL' behavior + +`DEL' by default is deleting char backward. + +But when `helm-ff-DEL-up-one-level-maybe' is non nil `DEL' behave +differently depending of helm-pattern contents, it go up one +level if pattern is a directory endings with \"/\" or disable HFF +auto update and delete char backward if pattern is a filename or +refer to a non existing path. Going up one level can be disabled +if necessary by deleting \"/\" at end of pattern using +\\\\[backward-char] and \\[helm-delete-minibuffer-contents]. + +Note that when deleting char backward, helm takes care of +disabling update letting you the time to edit your pattern for +e.g. renaming a file or creating a new file or directory. +When `helm-ff-auto-update-initial-value' is non nil you may want to +disable it temporarily, see [[Toggle auto-completion with `C-c DEL'][Toggle auto-completion with `C-c DEL']] for this. + +**** Use `\\\\[helm-find-files-down-last-level]' to walk back the resulting tree of all the `\\\\[helm-find-files-up-one-level]' or DEL you did + +The tree is reinitialized each time you browse a new tree with +`\\\\[helm-execute-persistent-action]' or by entering some pattern in the prompt. + +**** `RET' behavior + +It behaves differently depending on `helm-selection' (current candidate in helm-buffer): + +- candidate basename is \".\" => Open it in dired. +- candidate is a directory => Expand it. +- candidate is a file => Open it. + +If you have marked candidates and you press RET on a directory, +helm will navigate to this directory, if you want to exit with +RET with default action with these marked candidates, press RET +on a second time while you are on the root of this directory +e.g. \"/home/you/dir/.\" or press RET on any file which is not a +directory. You can also exit with default action at any moment +with `f1'. + +Note that when copying, renaming, etc. from `helm-find-files' the +destination file is selected with `helm-read-file-name'. + +To avoid confusion when using `read-file-name' or `read-directory-name', `RET' +follows its standard Emacs behaviour, i.e. it exits the minibuffer as soon as +you press `RET'. If you want the same behavior as in `helm-find-files', bind +`helm-ff-RET' to the `helm-read-file-map': + + (define-key helm-read-file-map (kbd \"RET\") 'helm-ff-RET) + +**** `TAB' behavior + +Normally `TAB' is bound to `helm-select-action' in helm-map which +display the action menu. + +You can change this behavior by setting in `helm-find-files-map' +a new command for `TAB': + + (define-key helm-find-files-map (kbd \"C-i\") 'helm-ff-TAB) + +It will then behave slighly differently +depending of `helm-selection': + +- candidate basename is \".\" => open the action menu. +- candidate is a directory => expand it (behave as \\\\[helm-execute-persistent-action]). +- candidate is a file => open action menu. + +Called with a prefix arg open menu unconditionally. + +*** Find file at point + +Helm uses `ffap' partially or completely to find file at point depending on the +value of `helm-ff-guess-ffap-filenames': if non-nil, support is complete +\(annoying), if nil, support is partial. + +Note that when the variable +`helm-ff-allow-non-existing-file-at-point' is non nil Helm will +insert the filename at point even if file with this name doesn't +exists. If non existing file at point ends with numbers prefixed +with \":\" the \":\" and numbers are stripped. + +**** Find file at line number + +When text at point is in the form of + + ~/elisp/helm/helm.el:1234 + +Helm finds this file at the indicated line number, here 1234. + +**** Find URL at point + +When a URL is found at point, Helm expands to that URL only. +Pressing `RET' opens that URL using `browse-url-browser-function'. + +**** Find e-mail address at point + +When an e-mail address is found at point, Helm expands to this e-mail address +prefixed with \"mailto:\". Pressing `RET' opens a message buffer with that +e-mail address. + +*** Quick pattern expansion + +**** Enter `~/' at end of pattern to quickly reach home directory + +**** Enter `/' at end of pattern to quickly reach the file system root + +**** Enter `./' at end of pattern to quickly reach `default-directory' + +\(As per its value at the beginning of the session.) + +If you already are in the `default-directory' this will move the cursor to the top. + +**** Enter `../' at end of pattern will reach upper directory, moving cursor to the top + +This is different from using `\\\\[helm-find-files-up-one-level]' in that it moves +the cursor to the top instead of remaining on the previous subdir name. + +**** Enter `..name/' at end of pattern to start a recursive search + +It searches directories matching \"name\" under the current directory, see the +\"Recursive completion on subdirectories\" section below for more details. + +**** Any environment variable (e.g. `$HOME') at end of pattern gets expanded + +**** Any valid filename yanked after pattern gets expanded + +**** Special case: URL at point + +The quick expansions do not take effect after end a URL, you must kill the +pattern first (`\\[helm-delete-minibuffer-contents]'). + +*** Helm-find-files supports fuzzy matching + +It starts from the third character of the pattern. + +For instance \"fob\" or \"fbr\" will complete \"foobar\" but \"fb\" needs a +third character in order to complete it. + +*** Use `\\[universal-argument] \\[helm-execute-persistent-action]' or `\\[helm-follow-action-forward]' to display an image + +*** `\\[helm-execute-persistent-action]' on a filename expands to that filename in the Helm buffer + +Second hit displays the buffer filename. +Third hit kills the buffer filename. +Note: `\\[universal-argument] \\[helm-execute-persistent-action]' displays the buffer directly. + +*** Browse images directories with `helm-follow-mode' and navigate up/down + +You can also use `helm-follow-action-forward' and `helm-follow-action-backward' with +`\\[helm-follow-action-forward]' and `\\[helm-follow-action-backward]' respectively. + +*** Toggle auto-completion with `\\[helm-ff-run-toggle-auto-update]' + +It is useful when trying to create a new file or directory and you don't want +Helm to complete what you are writing. + +Note: On a terminal, the default binding `C-' may not work. +In this case use `C-c '. + +*** You can create a new directory and a new file at the same time + +Simply write the path in the prompt and press `RET', e.g. +\"~/new/newnew/newnewnew/my_newfile.txt\". + +*** To create a new directory, append a \"/\" to the new name and press `RET' + +*** To create a new file, enter a filename not ending with \"/\" + +Note that when you enter a new name, this one is prefixed with +\[?] if you are in a writable directory. If you are in a directory +where you have no write permission the new file name is not +prefixed and is colored in red. There is not such distinction +when using tramp, new filename just appear on top of buffer. + +*** Recursive search from Helm-find-files + +**** You can use Helm-browse-project (see binding below) + +- With no prefix argument: +If the current directory is under version control with either git or hg and +helm-ls-git and/or helm-ls-hg are installed, it lists all the files under +version control. Otherwise it falls back to Helm-find-files. See +https://github.com/emacs-helm/helm-ls-git and +https://github.com/emacs-helm/helm-ls-hg. + +- With one prefix argument: +List all the files under this directory and other subdirectories +\(recursion) and this list of files will be cached. + +- With two prefix arguments: +Same but the cache is refreshed. + +**** You can start a recursive search with \"locate\" or \"find\" + +See \"Note\" in the [[Recursive completion on subdirectories][section on subdirectories]]. + +Using \"locate\", you can enable the local database with a prefix argument. If the +local database doesn't already exists, you will be prompted for its creation. +If it exists and you want to refresh it, give it two prefix args. + +When using locate the helm-buffer remains empty until you type something. +Regardless Helm uses the basename of the pattern entered in the helm-find-files +session by default. Hitting `\\[next-history-element]' should just kick in the +locate search with this pattern. If you want Helm to automatically do this, add +`helm-source-locate' to `helm-sources-using-default-as-input'. + +**** Recursive completion on subdirectories + +Starting from the directory you are currently browsing, it is possible to have +completion of all directories underneath. Say you are at \"/home/you/foo/\" and +you want to go to \"/home/you/foo/bar/baz/somewhere/else\", simply type +\"/home/you/foo/..else\" and hit `\\[helm-execute-persistent-action]' or enter +the final \"/\". Helm will then list all possible directories under \"foo\" +matching \"else\". + +Entering two spaces before \"else\" instead of two dots also works. + +Note: Completion on subdirectories uses \"locate\" as backend, you can configure +the command with `helm-locate-recursive-dirs-command'. Because this completion +uses an index, the directory tree displayed may be out-of-date and not reflect +the latest change until you update the index (using \"updatedb\" for \"locate\"). + +If for some reason you cannot use an index, the \"find\" command from +\"findutils\" can be used instead. It will be slower though. You need to pass +the basedir as first argument of \"find\" and the subdir as the value for +'-(i)regex' or '-(i)name' with the two format specs that are mandatory in +`helm-locate-recursive-dirs-command'. + +Examples: +- \"find %s -type d -name '*%s*'\" +- \"find %s -type d -regex .*%s.*$\" + +*** Insert filename at point or complete filename at point + +On insertion (not on completion, i.e. there is nothing at point): + +- `\\[helm-ff-run-complete-fn-at-point]': insert absolute file name. +- `\\[universal-argument] \\[helm-ff-run-complete-fn-at-point]': insert abbreviated file name. +- `\\[universal-argument] \\[universal-argument] \\[helm-ff-run-complete-fn-at-point]': insert relative file name. +- `\\[universal-argument] \\[universal-argument] \\[universal-argument] \\[helm-ff-run-complete-fn-at-point]': insert basename. + +On completion: + +- Target starts with \"~/\": insert abbreviate file name. +- target starts with \"/\" or \"[a-z]:/\": insert full path. +- Otherwise: insert relative file name. + +*** Use the wildcard to select multiple files + +Use of wilcard is supported to run an action over a set of files. + +Example: You can copy all the files with \".el\" extension by using \"*.el\" and +then run copy action. + +Similarly, \"**.el\" (note the two stars) will recursively select all \".el\" +files under the current directory. + +Note that when recursively copying files, you may have files with same name +dispatched across different subdirectories, so when copying them in the same +directory they will get overwritten. To avoid this Helm has a special action +called \"backup files\" that has the same behavior as the command line \"cp -f +--backup=numbered\": it allows you to copy many files with the same name from +different subdirectories into one directory. Files with same name are renamed +as follows: \"foo.txt.~1~\". Like with the --force option of cp, it is possible +to backup files in current directory. + +This command is available only when `dired-async-mode' is active. + +When using an action that involves an external backend (e.g. grep), using \"**\" +is not recommended (even thought it works fine) because it will be slower to +select all the files. You are better off leaving the backend to do it, it will +be faster. However, if you know you have not many files it is reasonable to use +this, also using not recursive wilcard (e.g. \"*.el\") is perfectly fine for +this. + +The \"**\" feature is active by default in the option `helm-file-globstar'. It +is different from the Bash \"shopt globstar\" feature in that to list files with +a named extension recursively you would write \"**.el\" whereas in Bash it would +be \"**/*.el\". Directory selection with \"**/\" like Bash \"shopt globstar\" +option is not supported yet. + +*** Query replace regexp on filenames + +Replace different parts of a file basename with something else. + +When calling this action you will be prompted twice as with +`query-replace', first for the matching expression of the text to +replace and second for the replacement text. Several facilities, +however, are provided to make the two prompts more powerfull. + +**** Syntax of the first prompt + +In addition to simple regexps, these shortcuts are available: + +- Basename without extension => \"%.\" +- Only extension => \".%\" +- Substring => \"%::\" +- Whole basename => \"%\" + +**** Syntax of the second prompt + +In addition to a simple string to use as replacement, here is what you can use: + +- A placeholder refering to what you have selected in the first prompt: \"\\@\". + +After this placeholder you can use a search-and-replace syntax à-la sed: + + \"\\@/// + +You can select a substring from the string represented by the placeholder: + + \"\\@::\" + +- A special character representing a number which is incremented: \"\\#\". + +- Shortcuts for `upcase', `downcase' and `capitalize' +are available as`%u', `%d' and `%c' respectively. + +**** Examples + +***** Recursively rename all files with \".JPG\" extension to \".jpg\" + +Use the `helm-file-globstar' feature described in [[Use the wildcard to select multiple files][recursive globbing]] +by entering \"**.JPG\" at the end of the Helm-find-files pattern, then hit +\\\\[helm-ff-query-replace-on-filenames]: First \"JPG\", then \"jpg\" +and hit `RET'. + +Alternatively you can enter \".%\" at the first prompt, then \"jpg\" and hit +`RET'. Note that when using this instead of using \"JPG\" at the first prompt, +all extensions will be renamed to \"jpg\" even if the extension of one of the +files is, say, \"png\". If you want to keep the original extension you can use +\"%d\" at the second prompt (downcase). + +***** Batch-rename files from number 001 to 00x + +Use \"\\#\" inside the second prompt. + +Example 1: To rename the files + + foo.jpg + bar.jpg + baz.jpg + +to + + foo-001.jpg + foo-002.jpg + foo-003.jpg + +use \"%.\" as matching regexp and \"foo-\\#\" as replacement string. + +Example 2: To rename the files + + foo.jpg + bar.jpg + baz.jpg + +to + + foo-001.jpg + bar-002.jpg + baz-003.jpg + +use as matching regexp \"%.\" and as replacement string \"\\@-\\#\". + +***** Replace a substring + +Use \"%::\". + +Example: To rename files + + foo.jpg + bar.jpg + baz.jpg + +to + + fOo.jpg + bAr.jpg + bAz.jpg + +use as matching regexp \"%:1:2\" and as replacement string \"%u\" (upcase). + +Note that you \*cannot* use \"%.\" and \".%\" along with substring replacement. + +***** Modify the string from the placeholder (\\@) + +- By substring, i.e. only using the substring of the placeholder: \"\\@::\". +The length of placeholder is used for when unspecified. + +Example 1: \"\\@:0:2\" replaces from the beginning to the second char of the placeholder. + +Example 2: \\@:2: replaces from the second char of the placeholder to the end. + +- By search-and-replace: \"\\@///\". + +Incremental replacement is also handled in . + +Example 3: \"\\@/foo/bar/\" replaces \"foo\" by \"bar\" in the placeholder. + +Example 4: \"\\@/foo/-\\#/\" replaces \"foo\" in the placeholder by 001, 002, etc. + +***** Clash in replacements (avoid overwriting files) + +When performing any of these replacement operations you may end up with same +names as replacement. In such cases Helm numbers the file that would otherwise +overwritten. For instance, should you remove the \"-m\" part from the files +\"emacs-m1.txt\", \"emacs-m2.txt\" and \"emacs-m3.txt\" you would end up with +three files named \"emacs.txt\", the second renaming overwriting first file, and +the third renaming overwriting second file and so on. Instead Helm will +automatically rename the second and third files as \"emacs(1).txt\" and +\"emacs(2).txt\" respectively. + +***** Query-replace on filenames vs. serial-rename action + +Unlike the [[Serial renaming][serial rename]] actions, the files renamed with +the query-replace action stay in their initial directory and are not moved to +the current directory. As such, using \"\\#\" to serial-rename files only makes +sense for files inside the same directory. It even keeps renaming files +with an incremental number in the next directories. + +*** Serial renaming + +You can use the serial-rename actions to rename, copy or symlink marked files to +a specific directory or in the current directory with all the files numbered +incrementally. + +- Serial-rename by renaming: +Rename all marked files with incremental numbering to a specific directory. + +- Serial-rename by copying: +Copy all marked files with incremental numbering to a specific directory. + +- Serial-rename by symlinking: +Symlink all marked files with incremental numbering to a specific directory. + +*** Edit marked files in a dired buffer + +You can open a dired buffer containing only marked files with `\\\\[helm-ff-run-marked-files-in-dired]'. +With a prefix argument you can open this same dired buffer in wdired mode for +editing. Note that wildcards are supported as well, so you can use e.g. +\"*.txt\" to select all \".txt\" files in the current directory or \"**.txt\" to +select all files recursively from the current directory. +See [[Use the wildcard to select multiple files]] section above. + +*** Defining default target directory for copying, renaming, etc + +You can customize `helm-dwim-target' to behave differently depending on the +windows open in the current frame. Default is to provide completion on all +directories associated to each window. + +*** Copying and renaming asynchronously + +If you have the async library installed (if you got Helm from MELPA you do), you +can use it for copying/renaming files by enabling `dired-async-mode'. + +Note that even when async is enabled, running a copy/rename action with a prefix +argument will execute action synchronously. Moreover it will follow the first +file of the marked files in its destination directory. + +When `dired-async-mode' is enabled, an additional action named \"Backup files\" +will be available. (Such command is not natively available in Emacs). +See [[Use the wildcard to select multiple files]] for details. + +*** Bookmark the `helm-find-files' session + +You can bookmark the `helm-find-files' session with `\\[helm-ff-bookmark-set]'. +You can later retrieve these bookmarks by calling `helm-filtered-bookmarks' +or, from the current `helm-find-files' session, by hitting `\\[helm-find-files-toggle-to-bookmark]'. + +*** Grep files from `helm-find-files' + +You can grep individual files from `helm-find-files' by using +\`\\\\[helm-ff-run-grep]'. This same command can also +recursively grep files from the current directory when called with a prefix +argument. In this case you will be prompted for the file extensions to use +\(grep backend) or the types of files to use (ack-grep backend). See the +`helm-grep-default-command' documentation to set this up. For compressed files +or archives, use zgrep with \`\\\\[helm-ff-run-zgrep]'. + +Otherwise you can use recursive commands like \`\\\\[helm-ff-run-grep-ag]' or `\\\\[helm-ff-run-git-grep]' +that are much faster than using `\\\\[helm-ff-run-grep]' with a prefix argument. +See `helm-grep-ag-command' and `helm-grep-git-grep-command' to set this up. + +You can also use \"id-utils\"' GID with \`\\\\[helm-ff-run-gid]' +by creating an ID index file with the \"mkid\" shell command. + +All those grep commands use the symbol at point as the default pattern. +Note that default is different from input (nothing is added to the prompt until +you hit `\\[next-history-element]'). + +**** Grepping on remote files + +On remote files grep is not well supported by TRAMP unless you suspend updates before +entering the pattern and re-enable it once your pattern is ready. +To toggle suspend-update, use `\\\\[helm-toggle-suspend-update]'. + +*** Execute Eshell commands on files + +Setting up aliases in Eshell allows you to set up powerful customized commands. + +Adding Eshell aliases to your `eshell-aliases-file' or using the +`alias' command from Eshell allows you to create personalized +commands not available in `helm-find-files' actions and use them +from `\\\\[helm-ff-run-eshell-command-on-file]'. + +Example: You want a command to uncompress some \"*.tar.gz\" files from `helm-find-files': + +1) Create an Eshell alias named, say, \"untargz\" with the command +\"alias untargz tar zxvf $*\". + +2) Now from `helm-find-files' select the \"*.tar.gz\" file (you can also +mark files if needed) and hit `\\\\[helm-ff-run-eshell-command-on-file]'. + +Note: When using marked files with this, the meaning of the prefix argument is +quite subtle. Say you have \"foo\", \"bar\" and \"baz\" marked; when you run +the alias command `example' on these files with no prefix argument it will run +`example' sequentially on each file: + +$ example foo +$ example bar +$ example baz + +With a prefix argument however it will apply `example' on all files at once: + +$ example foo bar baz + +Of course the alias command should support this. + +If you add %s to the command line %s will be replaced with the candidate, this mean you can +add extra argument to your command e.g. command -extra-arg %s or command %s -extra-arg. +If you want to pass many files inside %s, don't forget to use a prefix arg. + +You can also use special placeholders in extra-args, +see the specific info page once you hit `\\\\[helm-ff-run-eshell-command-on-file]'. + +*** Using TRAMP with `helm-find-files' to read remote directories + +`helm-find-files' works fine with TRAMP despite some limitations. + +- Grepping files is not very well supported when used incrementally. +See [[Grepping on remote files]]. + +- Locate does not work on remote directories. + +**** A TRAMP syntax crash course + +Please refer to TRAMP's documentation for more details. + +- Connect to host 192.168.0.4 as user \"foo\": + +/scp:192.168.0.4@foo: + +- Connect to host 192.168.0.4 as user \"foo\" on port 2222: + +/scp:192.168.0.4@foo#2222: + +- Connect to host 192.168.0.4 as root using multihops syntax: + +/ssh:192.168.0.4@foo|sudo:192.168.0.4: + +Note: You can also use `tramp-default-proxies-alist' when connecting often to +the same hosts. + +As a rule of thumb, prefer the scp method unless using multihops (which only +works with the ssh method), especially when copying large files. + +You need to hit `C-j' once on top of a directory on the first connection +to complete the pattern in the minibuffer. + +**** Display color for directories, symlinks etc... with tramp + +Starting at helm version 2.9.7 it is somewhat possible to +colorize fnames by listing files without loosing performances with +external commands (ls and awk) if your system is compatible. +For this you can use `helm-list-dir-external' as value +for `helm-list-directory-function'. + +See `helm-list-directory-function' documentation for more infos. + +**** Completing host + +As soon as you enter the first \":\" after method e.g =/scp:= you will +have some completion about previously used hosts or from your =~/.ssh/config= +file, hitting `\\[helm-execute-persistent-action]' or `right' on a candidate will insert this host in minibuffer +without addind the ending \":\", second hit insert the last \":\". +As soon the last \":\" is entered TRAMP will kick in and you should see the list +of candidates soon after. + +When connection fails, be sure to delete your TRAMP connection with M-x +`helm-delete-tramp-connection' before retrying. + +**** Editing local files as root + +Use the sudo method: + +\"/sudo:host:\" or simply \"/sudo::\". + +*** Attach files to a mail buffer (message-mode) + +If you are in a `message-mode' or `mail-mode' buffer, that action will appear +in action menu, otherwise it is available at any time with \\\\[helm-ff-run-mail-attach-files]. +It behaves as follows: + +- If you are in a (mail or message) buffer, files are attached there. + +- If you are not in a mail buffer but one or more mail buffers exist, you are +prompted to attach files to one of these mail buffers. + +- If you are not in a mail buffer and no mail buffer exists, +a new mail buffer is created with the attached files in it. + +*** Open files in separate windows + +When [[Marked candidates][marking]] multiple files or using [[Use the wildcard to select multiple files][wildcard]], helm allow opening all +this files in separate windows using an horizontal layout or a +vertical layout if you used a prefix arg, when no more windows can be +displayed in frame, next files are opened in background without being +displayed. When using \\\\[helm-ff-run-switch-other-window] the current +buffer is kept and files are displayed next to it with same behavior as above. +When using two prefix args, files are opened in background without beeing displayed. + +*** Expand archives as directories in a avfs directory + +If you have mounted your filesystem with mountavfs, +you can expand archives in the \"~/.avfs\" directory with \\\\[helm-execute-persistent-action]. + +*** Tramp archive support (emacs-27+ only) + +If your emacs have library tramp-archive.el, you can browse the +content of archives with emacs and BTW helm-find-files. However this beeing +experimental and not very fast, helm doesn't provide an automatic +expansion and detection of archives, you will have to add the final / +manually and may have to force update (\\\\[helm-refresh]) +or remove and add again the final / until tramp finish decompressing archive. + +*** Touch files + +In the completion buffer, you can choose the default which is the current-time, it is +the first candidate or the timestamp of one of the selected files. +If you need to use something else, use \\\\[next-history-element] and edit +the date in minibuffer. +It is also a way to quickly create a new file without opening a buffer, saving it +and killing it. +To touch more than one new file, separate you filenames with a comma (\",\"). +If one wants to create (touch) a new file with comma inside the name use a prefix arg, +this will prevent splitting the name and create multiple files. + +*** Delete files + +You can delete files without quitting helm with +`\\\\[helm-ff-persistent-delete]' or delete files and quit helm with `\\[helm-ff-run-delete-file]'. + +In the second method you can choose to +make this command asynchronous by customizing +\`helm-ff-delete-files-function'. + +_WARNING_: When deleting files asynchronously you will NOT be +WARNED if directories are not empty, that's mean non empty directories will +be deleted in background without asking. + +A good compromise is to trash your files +when using asynchronous method (see [[Trashing files][Trashing files]]). + +When choosing synchronous delete, you can allow recursive +deletion of directories with `helm-ff-allow-recursive-deletes'. +Note that when trashing (synchronous) you are not asked for recursive deletion. + +Note that `helm-ff-allow-recursive-deletes' have no effect when +deleting asynchronously. + +First method (persistent delete) is always synchronous. + +Note that when a prefix arg is given, trashing behavior is inversed. +See [[Trashing files][Trashing files]]. + +**** Trashing files + +If you want to trash your files instead of deleting them you can +set `delete-by-moving-to-trash' to non nil, like this your files +will be moved to trash instead of beeing deleted. + +You can reverse at any time the behavior of `delete-by-moving-to-trash' by using +a prefix arg with any of the delete files command. + +On GNULinux distributions, when navigating to a Trash directory you +can restore any file in ..Trash/files directory with the 'Restore +from trash' action you will find in action menu (needs the +trash-cli package installed for remote files, see [[Trashing remote files with tramp][Here]]). +You can as well delete files from Trash directories with the 'delete files from trash' +action. +If you want to know where a file will be restored, hit `M-i', you will find a trash info. + +Tip: Navigate to your Trash/files directories with `helm-find-files' and set a bookmark +there with \\\\[helm-ff-bookmark-set] for fast access to Trash. + +NOTE: Restoring files from trash is working only on system using +the [[http://freedesktop.org/wiki/Specifications/trash-spec][freedesktop trash specifications]]. + +_WARNING:_ + +If you have an ENV var XDG_DATA_HOME in your .profile or .bash_profile +and this var is set to something like $HOME/.local/share (like preconized) +`move-file-to-trash' may try to create $HOME/.local/share/Trash (literally) +and its subdirs in the directory where you are actually trying to trash files. +because `move-file-to-trash' is interpreting XDG_DATA_HOME literally instead +of evaling its value (with `substitute-in-file-name'). + +***** Trashing remote files with tramp + +Trashing remote files (or local files with sudo method) is disabled by default +because tramp is requiring the 'trash' command to be installed, if you want to +trash your remote files, customize `helm-trash-remote-files'. +The package on most GNU/Linux based distributions is trash-cli, it is available [[https://github.com/andreafrancia/trash-cli][here]]. + +NOTE: +When deleting your files with sudo method, your trashed files will not be listed +with trash-list until you log in as root. + +*** Checksum file + +Checksum is calculated with the md5sum, sha1sum, sha224sum, +sha256sum, sha384sum and sha512sum when available, otherwise the +Emacs function `secure-hash' is used but it is slow and may crash +Emacs and even the whole system as it eats all memory. So if +your system doesn't have the md5 and sha command line tools be +careful when checking sum of larges files e.g. isos. + +*** Ignored or boring files + +Helm-find-files can ignore files matching +`helm-boring-file-regexp-list' or files that are git ignored, you +can set this with `helm-ff-skip-boring-files' or +`helm-ff-skip-git-ignored-files'. + +** Commands +\\ +\\[helm-ff-run-locate]\t\tRun `locate' (`\\[universal-argument]' to specify locate database, `M-n' to insert basename of candidate). +\\[helm-ff-run-browse-project]\t\tBrowse project (`\\[universal-argument]' to recurse, `\\[universal-argument] \\[universal-argument]' to recurse and refresh database). +\\[helm-ff-run-find-sh-command]\t\tRun `find' shell command from this directory. +\\[helm-ff-run-grep]\t\tRun Grep (`\\[universal-argument]' to recurse). +\\[helm-ff-run-pdfgrep]\t\tRun Pdfgrep on marked files. +\\[helm-ff-run-zgrep]\t\tRun zgrep (`\\[universal-argument]' to recurse). +\\[helm-ff-run-grep-ag]\t\tRun AG grep on current directory. +\\[helm-ff-run-git-grep]\t\tRun git-grep on current directory. +\\[helm-ff-run-gid]\t\tRun gid (id-utils). +\\[helm-ff-run-etags]\t\tRun Etags (`\\[universal-argument]' to use thing-at-point, `\\[universal-argument] \\[universal-argument]' to reload cache). +\\[helm-ff-run-rename-file]\t\tRename Files (`\\[universal-argument]' to follow). +\\[helm-ff-run-query-replace-fnames-on-marked]\t\tQuery replace on marked files. +\\[helm-ff-run-copy-file]\t\tCopy Files (`\\[universal-argument]' to follow). +\\[helm-ff-run-byte-compile-file]\t\tByte Compile Files (`\\[universal-argument]' to load). +\\[helm-ff-run-load-file]\t\tLoad Files. +\\[helm-ff-run-symlink-file]\t\tSymlink Files. +\\[helm-ff-run-hardlink-file]\t\tHardlink files. +\\[helm-ff-run-relsymlink-file]\t\tRelative symlink Files. +\\[helm-ff-run-delete-file]\t\tDelete Files. +\\[helm-ff-run-touch-files]\t\tTouch files. +\\[helm-ff-run-kill-buffer-persistent]\t\tKill buffer candidate without leaving Helm. +\\[helm-ff-persistent-delete]\t\tDelete file without leaving Helm. +\\[helm-ff-run-switch-to-eshell]\t\tSwitch to Eshell. +\\[helm-ff-run-eshell-command-on-file]\t\tEshell command on file (`\\[universal-argument]' to apply on marked files, otherwise treat them sequentially). +\\[helm-ff-run-ediff-file]\t\tEdiff file. +\\[helm-ff-run-ediff-merge-file]\t\tEdiff merge file. +\\[helm-ff-run-complete-fn-at-point]\t\tComplete file name at point. +\\[helm-ff-run-switch-other-window]\t\tSwitch to other window. +\\[helm-ff-run-switch-other-frame]\t\tSwitch to other frame. +\\[helm-ff-run-open-file-externally]\t\tOpen file with external program (`\\[universal-argument]' to choose). +\\[helm-ff-run-preview-file-externally]\t\tPreview file with external program. +\\[helm-ff-run-open-file-with-default-tool]\t\tOpen file externally with default tool. +\\[helm-ff-rotate-left-persistent]\t\tRotate image left. +\\[helm-ff-rotate-right-persistent]\t\tRotate image right. +\\[helm-find-files-up-one-level]\t\tGo to parent directory. +\\[helm-find-files-history]\t\tSwitch to the visited-directory history. +\\[helm-ff-file-name-history]\t\tSwitch to file name history. +\\[helm-ff-properties-persistent]\t\tShow file properties in a tooltip. +\\[helm-mark-all]\t\tMark all visible candidates. +\\[helm-ff-run-toggle-auto-update]\t\tToggle auto-expansion of directories. +\\[helm-unmark-all]\t\tUnmark all candidates, visible and invisible ones. +\\[helm-ff-run-mail-attach-files]\t\tAttach files to message buffer. +\\[helm-ff-run-print-file]\t\tPrint file, (`\\[universal-argument]' to refresh printer list). +\\[helm-enlarge-window]\t\tEnlarge Helm window. +\\[helm-narrow-window]\t\tNarrow Helm window. +\\[helm-ff-run-toggle-basename]\t\tToggle basename/fullpath. +\\[helm-ff-run-find-file-as-root]\t\tFind file as root. +\\[helm-ff-run-find-alternate-file]\t\tFind alternate file. +\\[helm-ff-run-insert-org-link]\t\tInsert org link. +\\[helm-ff-bookmark-set]\t\tSet bookmark to current directory. +\\[helm-find-files-switch-to-bookmark]\t\tJump to bookmark list. +\\[helm-ff-sort-alpha]\t\tSort alphabetically +\\[helm-ff-sort-by-newest]\t\tSort by newest +\\[helm-ff-sort-by-size]\t\tSort by size") + +;;; Help for file-name-history +;; +;; +(defvar helm-file-name-history-help-message + "* Helm file name history + +** Tips +You can open directly the selected file and exit helm or preselect the file in helm-find-files, +see actions in action menu. + +You can toggle the view of deleted files, see commands below. + +** Commands +\\ +\\[helm-file-name-history-show-or-hide-deleted]\t\tToggle deleted files view.") + +;;; Help for `helm-read-file-name' +;; +;; +(defun helm-read-file-name-help-message () + (let ((name (if helm-alive-p + (assoc-default 'name (helm-get-current-source)) + "generic"))) + (format + "* Helm `%s' read file name completion + +This is `%s' read file name completion that have been \"helmized\" +because you have enabled [[Helm mode][helm-mode]]'. +Don't confuse this with `helm-find-files' which is a native helm command, +see [[Helm functions vs helmized Emacs functions]]. + +** Tips + +*** Navigation + +**** Enter `~/' at end of pattern to quickly reach home directory + +**** Enter `/' at end of pattern to quickly reach the file system root + +**** Enter `./' at end of pattern to quickly reach `default-directory' + +\(As per its value at the beginning of the session.) + +If you already are in the `default-directory' this will move the cursor to the top. + +**** Enter `../' at end of pattern will reach upper directory, moving cursor on top + +This is different from using `\\[helm-find-files-up-one-level]' in that it moves +the cursor to the top instead of remaining on the previous subdir name. + +**** You can complete with partial basename + +It starts from the third character of the pattern. + +For instance \"fob\" or \"fbr\" will complete \"foobar\" but \"fb\" needs a +third character in order to complete it. + +*** Persistent actions + +By default `helm-read-file-name' uses the persistent actions of `helm-find-files'. + +**** Use `\\[universal-argument] \\\\[helm-execute-persistent-action]' to display an image + +**** `\\\\[helm-execute-persistent-action]' on a filename will expand to this filename in Helm-buffer + +Second hit displays the buffer filename. +Third hit kills the buffer filename. +Note: `\\[universal-argument] \\\\[helm-execute-persistent-action]' displays the buffer directly. + +**** Browse images directories with `helm-follow-mode' and navigate up/down + +*** Delete characters backward + +When you want to delete characters backward, e.g. to create a new file or directory, +auto-update may come in the way when it keeps updating to an existent directory. +In that case, type `C-' and then `'. +This should not be needed when copying/renaming files because autoupdate is disabled +by default in that case. + +Note: On a terminal, the default binding `C-' may not work. +In this case use `C-c '. + +*** Create new directories and files + +**** You can create a new directory and a new file at the same time + +Simply write the path in prompt and press `RET', e.g. +\"~/new/newnew/newnewnew/my_newfile.txt\". + +**** To create a new directory, append a \"/\" at to the new name and press `RET' + +**** To create a new file, enter a filename not ending with \"/\" + +File and directory creation works only with some commands (e.g. `find-file') +and it will not work with others where it is not intended to return a file or +a directory \(e.g `list-directory'). + +*** Exiting minibuffer with empty string + +You can exit minibuffer with empty string with \\\\[helm-cr-empty-string]. +It is useful when some commands are prompting continuously until you enter an empty prompt. + +** Commands +\\ +\\[helm-find-files-up-one-level]\t\tGo to parent directory. +\\[helm-ff-run-toggle-auto-update]\t\tToggle auto-expansion of directories. +\\[helm-ff-run-toggle-basename]\t\tToggle basename. +\\[helm-ff-file-name-history]\t\tFile name history. +C/\\[helm-cr-empty-string]\t\tReturn empty string unless `must-match' is non-nil. +\\[helm-next-source]\t\tGo to next source. +\\[helm-previous-source]\t\tGo to previous source." + name name))) + +;;; Generic file help - Used by locate. +;; +;; +(defvar helm-generic-file-help-message + "* Helm Generic files + +** Tips + +*** Locate + +You can append to the search pattern any of the locate command line options, +e.g. -b, -e, -n , etc. See the locate(1) man page for more details. + +Some other sources (at the moment \"recentf\" and \"file in current directory\") +support the -b flag for compatibility with locate when they are used with it. + +When you enable fuzzy matching on locate with `helm-locate-fuzzy-match', the +search will be performed on basename only for efficiency (so don't add \"-b\" at +prompt). As soon as you separate the patterns with spaces, fuzzy matching will +be disabled and search will be done on the full filename. Note that in +multi-match, fuzzy is completely disabled, which means that each pattern is a +match regexp (i.e. \"helm\" will match \"helm\" but \"hlm\" will \*not* match +\"helm\"). + +*** Browse project + +When the current directory is not under version control, don't forget to refresh +the cache when files have been added/removed in the directory. + +*** Find command + +Recursively search files using the \"find\" shell command. + +Candidates are all filenames that match all given globbing patterns. This +respects the options `helm-case-fold-search' and +`helm-findutils-search-full-path'. + +You can pass arbitrary \"find\" options directly after a \"*\" separator. +For example, this would find all files matching \"book\" that are larger +than 1 megabyte: + + book * -size +1M + +** Commands +\\ +\\[helm-ff-run-toggle-basename]\t\tToggle basename. +\\[helm-ff-run-grep]\t\tRun grep (`\\[universal-argument]' to recurse). +\\[helm-ff-run-zgrep]\t\tRun zgrep. +\\[helm-ff-run-gid]\t\tRun GID (id-utils). +\\[helm-ff-run-pdfgrep]\t\tRun PDFgrep on marked files. +\\[helm-ff-run-copy-file]\t\tCopy file(s) +\\[helm-ff-run-rename-file]\t\tRename file(s). +\\[helm-ff-run-symlink-file]\t\tSymlink file(s). +\\[helm-ff-run-hardlink-file]\t\tHardlink file(s). +\\[helm-ff-run-delete-file]\t\tDelete file(s). +\\[helm-ff-run-byte-compile-file]\t\tByte compile Elisp file(s) (`\\[universal-argument]' to load). +\\[helm-ff-run-load-file]\t\tLoad Elisp file(s). +\\[helm-ff-run-ediff-file]\t\tEdiff file. +\\[helm-ff-run-ediff-merge-file]\t\tEdiff-merge file. +\\[helm-ff-run-switch-other-window]\t\tSwitch to other window. +\\[helm-ff-properties-persistent]\t\tShow file properties. +\\[helm-ff-run-etags]\t\tRun etags (`\\[universal-argument]' to use tap, `\\[universal-argument] \\[universal-argument]' to reload the database). +\\[helm-ff-run-open-file-externally]\t\tOpen file with external program (`\\[universal-argument]' to choose). +\\[helm-ff-run-open-file-with-default-tool]\t\tOpen file externally with default tool. +\\[helm-ff-run-insert-org-link]\t\tInsert org link.") + +;;; Grep help +;; +;; +(defvar helm-grep-help-message + "* Helm Grep + +** Tips + +*** Use a prefix argument to grep recursively + +With Helm supporting git-grep and AG however, you are better off using one of +them for recursive searches. + +*** You can use wild cards when selecting files (e.g. \"*.el\") + +*** You can grep in many different directories by marking files or using wild cards + +*** You can save the result in a `helm-grep-mode' buffer + +See [[Commands][commands]] below. + +Once in that buffer you can use \"emacs-wgrep\" (external package not bundled with Helm) +to edit your changes. + +*** Helm-grep supports multi-matching + +\(Starting from version 1.9.4.) + +Simply add a space between each pattern as for most Helm commands. + +*** See full path of selected candidate + +Add (helm-popup-tip-mode 1) in your init file or enable it interactively with +M-x helm-popup-tip-mode. + +*** Open file in other window + +The command \\\\[helm-grep-run-other-window-action] allow you to open file +in other window horizontally or vertically if a prefix arg is supplied. + +*** Performance over TRAMP + +Grepping works but it is badly supported as TRAMP doesn't support multiple +processes running in a short delay (less than 5s) among other things. + +Helm uses a special hook to suspend the process automatically while you are +typing. Even if Helm handles this automatically by delaying each process by 5s, +you are adviced to this manually by hitting `\\\\[helm-toggle-suspend-update]' (suspend process) before +typing, and hit again `\\\\[helm-toggle-suspend-update]' when the regexp is ready to send to the remote +process. For simple regexps, there should be no need for this. + +Another solution is to not use TRAMP at all and mount your remote file system via +SSHFS. + +* Helm GID + +** Tips + +Helm-GID reads the database created with the `mkid' command from id-utils. +The name of the database file can be customized with `helm-gid-db-file-name', it +is usually \"ID\". + +Helm-GID use the symbol at point as default-input. This command is also +accessible from `helm-find-files' which allow you to navigate to another +directory to consult its database. + +Note: Helm-GID supports multi-matches but only the last pattern entered will be +highlighted since there is no ~--color~-like option in GID itself. + +* Helm AG + +** Tips + +Helm-AG is different from grep or ack-grep in that it works on a directory and +not on a list of files. + +You can ignore files and directories with a \".agignore\" file, local to a +directory or global when placed in the home directory. \(See the AG man page for +more details.) That file follows the same syntax as `helm-grep-ignored-files' +and `helm-grep-ignored-directories'. + +As always you can access Helm AG from `helm-find-files'. + +Starting with version 0.30, AG accepts one or more TYPE arguments on its command +line. Helm provides completion on these TYPE arguments when available with your +AG version. Use a prefix argument when starting a Helm-AG session to enable this +completion. + +Note: You can mark several types to match in the AG query. The first AG +versions providing this feature allowed only one type, so in this case only the +last mark will be used. + +* Helm git-grep + +Helm-git-grep searches the current directory, i.e the default directory or the +directory in Helm-find-files. If this current directory is a subdirectory of a +project and you want to also match parent directories (i.e the whole project), +use a prefix argument. + +** Commands +\\ +\\[helm-goto-next-file]\t\tNext File. +\\[helm-goto-precedent-file]\t\tPrevious File. +\\[helm-yank-text-at-point]\t\tYank text at point in minibuffer. +\\[helm-grep-run-other-window-action]\t\tJump to other window. +\\[helm-grep-run-other-frame-action]\t\tJump to other frame. +\\[helm-grep-run-default-action]\t\tRun default action (same as `RET'). +\\[helm-grep-run-save-buffer]\t\tSave to a `helm-grep-mode' enabled buffer.") + +;;; PDF grep help +;; +;; +(defvar helm-pdfgrep-help-message + "* Helm PDFgrep Map + +** Commands +\\ +\\[helm-goto-next-file]\t\tNext file. +\\[helm-goto-precedent-file]\t\tPrevious file. +\\[helm-yank-text-at-point]\t\tYank text at point in minibuffer.") + +;;; Etags help +;; +;; +(defvar helm-etags-help-message + "* Helm Etags Map + +** Commands +\\ +\\[helm-goto-next-file]\t\tNext file. +\\[helm-goto-precedent-file]\t\tPrevious file. +\\[helm-yank-text-at-point]\t\tYank text at point in minibuffer.") + +;;; UCS help +;; +;; +(defvar helm-ucs-help-message + "* Helm UCS + +** Tips + +Use commands below to insert unicode characters in current buffer without +leaving Helm. + +** Commands +\\ +\\[helm-ucs-persistent-insert]\t\tInsert character. +\\[helm-ucs-persistent-forward]\t\tForward character. +\\[helm-ucs-persistent-backward]\t\tBackward character. +\\[helm-ucs-persistent-delete]\t\tDelete character backward. +\\[helm-ucs-persistent-insert-space]\t\tInsert space.") + +;;; Bookmark help +;; +;; +(defvar helm-bookmark-help-message + "* Helm bookmark name + +** Commands +\\ +\\[helm-bookmark-run-jump-other-window]\t\tJump other window. +\\[helm-bookmark-run-delete]\t\tDelete bookmark. +\\[helm-bookmark-run-edit]\t\tEdit bookmark. +\\[helm-bookmark-toggle-filename]\t\tToggle bookmark location visibility.") + +;;; Eshell command on file help +;; +;; +(defvar helm-esh-help-message + "* Helm Eshell on file + +** Tips + +*** Pass extra arguments after filename + +Normally the command or alias will be called with file as argument. For instance + + candidate_file + +But you can also pass an argument or more after \"candidate_file\" like this: + + %s [extra_args] + +\"candidate_file\" will be added at \"%s\" and the command will look at this: + + candidate_file [extra_args] + +**** Use placeholders in extra arguments + +placeholder for file without extension: \\@ +placeholder for incremental number: \\# + +\"candidate_file\" will be added at \"%s\" and \\@ but without extension. + + + +\"candidate_file\" will be added at \"%s\" and \\# will be replaced by an incremental number. + + %s \\# + +Here examples: + +Say you want to use the =convert= command to convert all your .png files in a directory to .jpg. + +This will convert all your files to jpg keeping the same basename. + + convert %s \\@.jpg + +This will convert all your files to foo-001.jpg, foo-002.jpg etc... + + convert %s foo-\\#.jpg + +You can of course combine both placeholders if needed. + + convert %s \\@-\\#.jpg + +*** Specify marked files as arguments + +Example: + + file1 file2... + +Call `helm-find-files-eshell-command-on-file' with one prefix argument. Otherwise +you can pass one prefix argument from the command selection buffer. + +Note: This does not work on remote files. + +With two prefix-args the output is printed to the `current-buffer'. + +With no prefix argument or a prefix argument value of '(16) (`\\[universal-argument] \\[universal-argument]') +the command is called once for each file like this: + + file1 + file2 + ... + +** Commands +\\") + +;;; Ido virtual buffer help +;; +;; +(defvar helm-buffers-ido-virtual-help-message + "* Helm Ido virtual buffers + +** Commands +\\ +\\[helm-ff-run-switch-other-window]\t\tSwitch to other window. +\\[helm-ff-run-switch-other-frame]\t\tSwitch to other frame. +\\[helm-ff-run-grep]\t\tGrep file. +\\[helm-ff-run-zgrep]\t\tZgrep file. +\\[helm-ff-run-delete-file]\t\tDelete file. +\\[helm-ff-run-open-file-externally]\t\tOpen file externally.") + +;;; Moccur help +;; +;; +(defvar helm-moccur-help-message + "* Helm Moccur + +** Tips + +*** Matching + +Multiple regexp matching is allowed, simply enter a space to separate the regexps. + +Matching empty lines is supported with the regexp \"^$\", you then get the +results displayed as the buffer-name and the line number only. You can +save and edit these results, i.e. add text to the empty line. + +*** Automatically match symbol at point + +Helm can automatically match the symbol at point while keeping the minibuffer +empty, ready to be written to. This behaviour is disabled by default. To +enable this you need to add `helm-source-occur' and `helm-source-moccur' to +`helm-sources-using-default-as-input'. + +*** Jump to the corresponding line in the searched buffer + +You can do this with `\\\\[helm-execute-persistent-action]' (persistent-action), to do it repeatedly +you can use `\\\\[helm-follow-action-forward]' and `\\\\[helm-follow-action-backward]' or enable `helm-follow-mode' with `\\\\[helm-follow-mode]'. +Follow mode is enabled by default in helm-occur. + +*** Switch to buffer in other window + +The command \\\\[helm-moccur-run-goto-line-ow] allow you to switch to buffer +in other window horizontally or vertically if a prefix arg is supplied. + +*** Save the results + +Similarly to Helm-grep, you can save the results with `\\\\[helm-occur-run-save-buffer]'. +Once in the saved buffer, you can edit it, see [[Edit a saved buffer][below]]. + +Of course if you don't save the results, you can resume the Helm session with +`helm-resume'. + +*** Refresh the resumed session + +When the buffer(s) where you ran helm-(m)occur get(s) modified, the Helm buffer +will flash red as a warning. You can refresh the buffer by running `\\\\[helm-refresh]'. +This can be done automatically by customizing `helm-moccur-auto-update-on-resume'. + +*** Refresh a saved buffer + +Type `g' to update the buffer. + +*** Edit a saved buffer + +First, install wgrep (https://github.com/mhayashi1120/Emacs-wgrep) and then: + +1) `C-c C-p' (`wgrep-change-to-wgrep-mode') to edit the buffer(s). +2) `C-x C-s' to save your changes. + +Tip: Use the excellent iedit (https://github.com/victorhge/iedit) to modify all +occurences at once in the buffer. + +*** Search in region + +When searching in current-buffer with `helm-occur', if a region +is found helm will search in this region only. If you marked +this region with `mark-defun' the symbol that was at point before +marking defun will be used when `helm-source-occur' is member of +`helm-sources-using-default-as-input'. + +*** Switch to next or previous source + +See [[Moving in `helm-buffer'][Moving in `helm-buffer']]. + +** Commands +\\ +\\[helm-occur-run-goto-line-ow]\t\tGo to line in other window. +\\[helm-occur-run-goto-line-of]\t\tGo to line in new frame. +\\[helm-occur-run-save-buffer]\t\tSave results in new buffer.") +;;; Helm Top +;; +;; +(defvar helm-top-help-message + "* Helm Top + +** Commands +\\ +\\[helm-top-run-sort-by-com]\t\tSort by commands. +\\[helm-top-run-sort-by-cpu]\t\tSort by CPU usage. +\\[helm-top-run-sort-by-user]\t\tSort alphabetically by user. +\\[helm-top-run-sort-by-mem]\t\tSort by memory.") + +;;; Helm Elisp package +;; +;; +(defvar helm-el-package-help-message + "* Helm Elisp package + +** Tips + +*** Compile all your packages asynchronously + +If you use async (if you have installed Helm from MELPA you do), only \"helm\", +\"helm-core\", and \"magit\" are compiled asynchronously. If you want all your +packages compiled asynchronously, add this to your init file: + + (setq async-bytecomp-allowed-packages '(all)) + +*** Upgrade Elisp packages + +On initialization (when Emacs is fetching packages on remote), if Helm finds +packages to upgrade, it will start in the upgradable packages view showing the packages +available for upgrade. + +On subsequent runs, you will have to refresh the list with `C-c \\[universal-argument]'. If Helm +finds upgrades you can switch to upgrade view (see below) to see what packages +are available for upgrade or simply hit `C-c U' to upgrade them all. + +To see upgradable packages hit `M-U'. + +Then you can install all upgradable packages with the \"upgrade all\" action +\(`C-c \\[universal-argument]'), or upgrade only specific packages by marking them and running the +\"upgrade\" action (visible only when there are upgradable packages). Of course +you can upgrade a single package by just running the \"upgrade\" action without +marking it (`C-c u' or `RET') . + +\*Warning:* You are strongly advised to \*restart* Emacs after \*upgrading* packages. + +*** Meaning of flags prefixing packages + +\(Emacs ≥25) + +- The flag \"S\" that prefixes package names means that the packages belong to `package-selected-packages'. + +- The flag \"U\" that prefix package names mean that this package is no more needed. + +** Commands +\\ +\\[helm-el-package-show-all]\t\tShow all packages. +\\[helm-el-package-show-installed]\t\tShow installed packages only. +\\[helm-el-package-show-uninstalled]\t\tShow non-installed packages only. +\\[helm-el-package-show-upgrade]\t\tShow upgradable packages only. +\\[helm-el-package-show-built-in]\t\tShow built-in packages only. +\\[helm-el-run-package-install]\t\tInstall package(s). +\\[helm-el-run-package-reinstall]\t\tReinstall package(s). +\\[helm-el-run-package-uninstall]\t\tUninstall package(s). +\\[helm-el-run-package-upgrade]\t\tUpgrade package(s). +\\[helm-el-run-package-upgrade-all]\t\tUpgrade all packages. +\\[helm-el-run-visit-homepage]\t\tVisit package homepage.") + +;;; Helm M-x +;; +;; +(defvar helm-M-x-help-message + "* Helm M-x + +** Tips + +*** You can get help on any command with persistent action (\\[helm-execute-persistent-action]) + +*** Prefix arguments + +You must pass prefix arguments \*after* starting `helm-M-x'. A mode-line +counter will display the number of given prefix arguments. + +If you pass prefix arguments before running `helm-M-x', it will be displayed in the prompt. +The first `\\[universal-argument]' after `helm-M-x' clears those prefix arguments.") + +;;; Helm imenu +;; +;; +(defvar helm-imenu-help-message + "* Helm Imenu + +** Commands +\\ +\\[helm-imenu-next-section]\t\tGo to next section. +\\[helm-imenu-previous-section]\t\tGo to previous section.") + +;;; Helm colors +;; +;; +(defvar helm-colors-help-message + "* Helm colors + +** Commands +\\ +\\[helm-color-run-insert-name]\t\tInsert the entry name. +\\[helm-color-run-kill-name]\t\tKill the entry name. +\\[helm-color-run-insert-rgb]\t\tInsert entry in RGB format. +\\[helm-color-run-kill-rgb]\t\tKill entry in RGB format.") + +;;; Helm Semantic +;; +;; +(defvar helm-semantic-help-message + "* Helm Semantic + +** Commands +\\") + +;;; Helm kmacro +;; +;; +(defvar helm-kmacro-help-message + "* Helm kmacro + +** Tips + +- Start recording a kmacro with `f3'. +- End the kmacro recording with `f4'. +- Run `helm-execute-kmacro' to list all your kmacros. + +Use persistent action to run your kmacro as many time as needed. +You can browse the kmacros with `helm-next-line' and `helm-previous-line'. + +Note: You can't record keys running Helm commands except `helm-M-x', under the +condition that you don't choose a command using Helm completion. + +** Commands +\\") + +;;; Kill ring +;; +;; +(defvar helm-kill-ring-help-message + "* Helm kill ring + +** Tips + +Every Helm session lets you save a candidate to the kill-ring / clipboard / +primary-selection with `\\\\[helm-kill-selection-and-quit]'. + +To save space, Helm-kill-ring truncates the candidates longer than +`helm-kill-ring-max-offset'. +`\\\\[helm-kill-ring-kill-selection]' then saves the whole +text and not the truncated value. The view of truncated candidates can be +toggled; see the command list below. + +As opposed to `yank', numeric prefix arguments are ignored with +`helm-show-kill-ring': there is no need for them since selection happens within +Helm. Moreover Helm has [[Shortcuts for executing the default action on the n-th candidate][Shortcuts for executing the default action on the n-th candidate]]. + +It is recommended to globally bind `M-y' to `helm-show-kill-ring'. Once in the +Helm-kill-ring session you can navigate to next/previous line with `M-y' and +`M-u' for convenience. Of course `\\[helm-next-line]' and `\\[helm-previous-line]' are still available. + +It is possible to delete candidates from the kill ring with `\\\\[helm-kill-ring-delete]' +but also persistently with `\\\\[helm-kill-ring-run-persistent-delete]'. + +You can concatenate marked candidates and yank them in the current +buffer, thus creating a new entry in the kill ring. Candidates are +concatenated with `helm-kill-ring-separator' as default but you can +change interactively the separator while yanking by using two prefix +args. When you have something else than \"\\n\" as default value for +`helm-kill-ring-separator' and you want to use \"\\n\" from prompt, use +`C-q C-j' to enter a newline in prompt. + +To not push a new entry in the kill ring, use `\\\\[helm-copy-to-buffer]' instead of RET +\(note that you can't change separator with this). + +When inserting candidates with the default action (`RET'), `point' is placed at +the end of the candidate and `mark' at the beginning. You can revert this behavior +by using a prefix argument, i.e. `C-u RET', like the regular `yank' command does. + +** Commands +\\ +\\[helm-next-line]\t\tNext line. +\\[helm-previous-line]\t\tPrevious line. +\\[helm-kill-ring-delete]\t\tDelete entry. +\\[helm-kill-ring-toggle-truncated]\t\tToggle truncated view of candidate. +\\[helm-kill-ring-kill-selection]\t\tKill non-truncated of selection.") + +;;; Completing-read +;; +(defun helm-comp-read-help-message () + (let ((com (assoc-default 'name (helm-get-current-source)))) + (format + "* Helm completing-read completion for `%s' + +Command `%s' is using a `completing-read' for completion on your input, +this completion have been \"helmized\" because you have enabled [[Helm mode][helm-mode]]'. + +** Tips + +*** Disabling or use something else than helm for completion of some commands + +You can disable helm completion or use something else for specific commands of your choice, +for this customize variable `helm-completing-read-handlers-alist'. + +*** Exiting minibuffer with empty string + +You can exit minibuffer with empty string with \\\\[helm-cr-empty-string]. +It is useful when some commands are prompting continuously until you enter an empty prompt. + +** Commands +\\ +\\[helm-cr-empty-string]\t\tExit minibuffer with empty string." + com com))) + + +;;; Mode line strings +;; +;; +;;;###autoload +(defvar helm-comp-read-mode-line "\ +\\\ +C/\\[helm-cr-empty-string]:Empty \ +\\\ +\\[helm-help]:Help \ +\\[helm-select-action]:Act \ +\\[helm-maybe-exit-minibuffer]/\ +f1/f2/f-n:NthAct \ +\\[helm-toggle-suspend-update]:Tog.suspend \ +\\[helm-customize-group]:Conf") + +;;;###autoload +(defvar helm-read-file-name-mode-line-string "\ +\\\ +\\[helm-help]:Help \ +C/\\[helm-cr-empty-string]:Empty \ +\\\ +\\[helm-select-action]:Act \ +\\[helm-maybe-exit-minibuffer]/\ +f1/f2/f-n:NthAct \ +\\[helm-toggle-suspend-update]:Tog.suspend \ +\\[helm-customize-group]:Conf" + "String displayed in mode-line in `helm-source-find-files'.") + +;;;###autoload +(defvar helm-top-mode-line "\ +\\\ +\\[helm-help]:Help \ +\\\ +\\[helm-select-action]:Act \ +\\[helm-maybe-exit-minibuffer]/\ +f1/f2/f-n:NthAct \ +\\[helm-toggle-suspend-update]:Tog.suspend \ +\\[helm-customize-group]:Conf") + + +(provide 'helm-help) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-help.el ends here diff --git a/elpa/helm-20191031.839/helm-id-utils.el b/elpa/helm-20191031.839/helm-id-utils.el new file mode 100644 index 00000000..8752fd55 --- /dev/null +++ b/elpa/helm-20191031.839/helm-id-utils.el @@ -0,0 +1,131 @@ +;;; helm-id-utils.el --- Helm interface for id-utils. -*- lexical-binding: t -*- + +;; Copyright (C) 2015 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'helm-grep) +(require 'helm-help) + +(defgroup helm-id-utils nil + "ID-Utils related Applications and libraries for Helm." + :group 'helm) + +(defcustom helm-gid-program "gid" + "Name of gid command (usually `gid'). +For Mac OS X users, if you install GNU coreutils, the name `gid' +might be occupied by `id' from GNU coreutils, and you should set +it to correct name (or absolute path), for example, if using +MacPorts to install id-utils, it should be `gid32'." + :group 'helm-id-utils + :type 'file) + +(defcustom helm-gid-db-file-name "ID" + "Name of a database file created by `mkid' command from `ID-utils'." + :group 'helm-id-utils + :type 'string) + +(defun helm-gid-candidates-process () + (let* ((patterns (helm-mm-split-pattern helm-pattern)) + (default-com (format "%s -r %s" helm-gid-program + (shell-quote-argument (car patterns)))) + (cmd (helm-aif (cdr patterns) + (concat default-com + (cl-loop for p in it + concat (format " | grep --color=always %s" + (shell-quote-argument p)))) + default-com)) + (proc (start-process-shell-command + "gid" helm-buffer cmd))) + (set (make-local-variable 'helm-grep-last-cmd-line) cmd) + (prog1 proc + (set-process-sentinel + proc (lambda (_process event) + (when (string= event "finished\n") + (helm-maybe-show-help-echo) + (with-helm-window + (setq mode-line-format + '(" " mode-line-buffer-identification " " + (:eval (format "L%s" (helm-candidate-number-at-point))) " " + (:eval (propertize + (format "[Helm Gid process finished - (%s results)]" + (max (1- (count-lines + (point-min) (point-max))) + 0)) + 'face 'helm-locate-finish)))) + (force-mode-line-update)) + (helm-log "Error: Gid %s" + (replace-regexp-in-string "\n" "" event)))))))) + +(defun helm-gid-filtered-candidate-transformer (candidates _source) + ;; "gid -r" may add dups in some rare cases. + (cl-loop for c in (helm-fast-remove-dups candidates :test 'equal) + collect (helm-grep--filter-candidate-1 c))) + +(defclass helm-gid-source (helm-source-async) + ((header-name + :initform + (lambda (name) + (concat name " [" (helm-attr 'db-dir) "]"))) + (db-dir :initarg :db-dir + :initform nil + :custom string + :documentation " Location of ID file.") + (candidates-process :initform #'helm-gid-candidates-process) + (filtered-candidate-transformer + :initform #'helm-gid-filtered-candidate-transformer) + (candidate-number-limit :initform 99999) + (action :initform (helm-make-actions + "Find File" 'helm-grep-action + "Find file other frame" 'helm-grep-other-frame + "Save results in grep buffer" 'helm-grep-save-results + "Find file other window" 'helm-grep-other-window)) + (persistent-action :initform 'helm-grep-persistent-action) + (history :initform 'helm-grep-history) + (nohighlight :initform t) + (help-message :initform 'helm-grep-help-message) + (requires-pattern :initform 2))) + +;;;###autoload +(defun helm-gid () + "Preconfigured helm for `gid' command line of `ID-Utils'. +Need A database created with the command `mkid' +above `default-directory'. +Need id-utils as dependency which provide `mkid', `gid' etc... +See ." + (interactive) + (let* ((db (locate-dominating-file + default-directory + helm-gid-db-file-name)) + (helm-grep-default-directory-fn + (lambda () default-directory)) + (helm--maybe-use-default-as-input t)) + (cl-assert db nil "No DataBase found, create one with `mkid'") + (helm :sources (helm-make-source "Gid" 'helm-gid-source + :db-dir db) + :buffer "*helm gid*" + :keymap helm-grep-map + :truncate-lines helm-grep-truncate-lines))) + +(provide 'helm-id-utils) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-id-utils ends here diff --git a/elpa/helm-20191031.839/helm-imenu.el b/elpa/helm-20191031.839/helm-imenu.el new file mode 100644 index 00000000..2ff19723 --- /dev/null +++ b/elpa/helm-20191031.839/helm-imenu.el @@ -0,0 +1,367 @@ +;;; helm-imenu.el --- Helm interface for Imenu -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'cl-lib) +(require 'helm) +(require 'helm-lib) +(require 'imenu) +(require 'helm-utils) +(require 'helm-help) + + +(defgroup helm-imenu nil + "Imenu related libraries and applications for helm." + :group 'helm) + +(defcustom helm-imenu-delimiter " / " + "Delimit types of candidates and his value in `helm-buffer'." + :group 'helm-imenu + :type 'string) + +(defcustom helm-imenu-execute-action-at-once-if-one + #'helm-imenu--execute-action-at-once-p + "Goto the candidate when only one is remaining." + :group 'helm-imenu + :type 'function) + +(defcustom helm-imenu-all-buffer-assoc nil + "Major mode association alist for `helm-imenu-in-all-buffers'. +Allow `helm-imenu-in-all-buffers' searching in these associated buffers +even if they are not derived from each other. +The alist is bidirectional, i.e no need to add '((foo . bar) (bar . foo)) +only '((foo . bar)) is needed." + :type '(alist :key-type symbol :value-type symbol) + :group 'helm-imenu) + +(defcustom helm-imenu-in-all-buffers-separate-sources t + "Display imenu index of each buffer in its own source when non-nil. + +When nil all candidates are displayed in a single source. + +NOTE: Each source will have as name \"Imenu \". +`helm-source-imenu-all' will not be set, however it will continue +to be used as a flag for using default as input, if you do not want +this behavior, remove it from `helm-sources-using-default-as-input' +even if not using a single source to display imenu in all buffers." + :type 'boolean + :group 'helm-imenu) + +(defcustom helm-imenu-type-faces + '(("^Variables$" . font-lock-variable-name-face) + ("^\\(Function\\|Functions\\|Defuns\\)$" . font-lock-function-name-face) + ("^\\(Types\\|Provides\\|Requires\\|Classes\\|Class\\|Includes\\|Imports\\|Misc\\|Code\\)$" . font-lock-type-face)) + "Faces for showing type in helm-imenu. +This is a list of cons cells. The cdr of each cell is a face to be used, +and it can also just be like \\='(:foreground \"yellow\"). +Each car is a regexp match pattern of the imenu type string." + :group 'helm-faces + :type '(repeat + (cons + (regexp :tag "Imenu type regexp pattern") + (sexp :tag "Face")))) + +(defcustom helm-imenu-extra-modes nil + "Extra modes where helm-imenu-in-all-buffers should look into." + :group 'helm-imenu + :type '(repeat symbol)) + +;;; keymap +(defvar helm-imenu-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "M-") 'helm-imenu-next-section) + (define-key map (kbd "M-") 'helm-imenu-previous-section) + map)) + +(defcustom helm-imenu-lynx-style-map nil + "Use Arrow keys to jump to occurences." + :group 'helm-imenu + :type 'boolean + :set (lambda (var val) + (set var val) + (if val + (progn + (define-key helm-imenu-map (kbd "") 'helm-execute-persistent-action) + (define-key helm-imenu-map (kbd "") 'helm-maybe-exit-minibuffer)) + (define-key helm-imenu-map (kbd "") nil) + (define-key helm-imenu-map (kbd "") nil)))) + +(defun helm-imenu-next-or-previous-section (n) + (with-helm-window + (let* ((fn (lambda () + (car (split-string + (buffer-substring + (point-at-bol) (point-at-eol)) + helm-imenu-delimiter)))) + (curtype (funcall fn)) + (stop-fn (if (> n 0) + #'helm-end-of-source-p + #'helm-beginning-of-source-p))) + (while (and (not (funcall stop-fn)) + (string= curtype (funcall fn))) + (forward-line n)) + (helm-mark-current-line) + (helm-follow-execute-persistent-action-maybe)))) + +(defun helm-imenu-next-section () + (interactive) + (helm-imenu-next-or-previous-section 1)) + +(defun helm-imenu-previous-section () + (interactive) + (helm-imenu-next-or-previous-section -1)) + + +;;; Internals +(defvar helm-cached-imenu-alist nil) +(make-variable-buffer-local 'helm-cached-imenu-alist) + +(defvar helm-cached-imenu-candidates nil) +(make-variable-buffer-local 'helm-cached-imenu-candidates) + +(defvar helm-cached-imenu-tick nil) +(make-variable-buffer-local 'helm-cached-imenu-tick) + +(defvar helm-imenu--in-all-buffers-cache nil) + +(defvar helm-source-imenu nil "See (info \"(emacs)Imenu\")") +(defvar helm-source-imenu-all nil) + +(defclass helm-imenu-source (helm-source-sync) + ((candidates :initform 'helm-imenu-candidates) + (candidate-transformer :initform 'helm-imenu-transformer) + (persistent-action :initform 'helm-imenu-persistent-action) + (persistent-help :initform "Show this entry") + (nomark :initform t) + (keymap :initform helm-imenu-map) + (help-message :initform 'helm-imenu-help-message) + (action :initform 'helm-imenu-action) + (group :initform 'helm-imenu))) + +(defcustom helm-imenu-fuzzy-match nil + "Enable fuzzy matching in `helm-source-imenu'." + :group 'helm-imenu + :type 'boolean + :set (lambda (var val) + (set var val) + (setq helm-source-imenu + (helm-make-source "Imenu" 'helm-imenu-source + :fuzzy-match helm-imenu-fuzzy-match)))) + +(defun helm-imenu--maybe-switch-to-buffer (candidate) + (let ((cand (cdr candidate))) + (helm-aif (and (markerp cand) (marker-buffer cand)) + (switch-to-buffer it)))) + +(defun helm-imenu--execute-action-at-once-p () + (let ((cur (helm-get-selection)) + (mb (with-helm-current-buffer + (save-excursion + (goto-char (point-at-bol)) + (point-marker))))) + (if (equal (cdr cur) mb) + (prog1 nil + (helm-set-pattern "") + (helm-force-update)) + t))) + +(defun helm-imenu-action (candidate) + "Default action for `helm-source-imenu'." + (helm-log-run-hook 'helm-goto-line-before-hook) + (helm-imenu--maybe-switch-to-buffer candidate) + (imenu candidate) + ;; If semantic is supported in this buffer + ;; imenu used `semantic-imenu-goto-function' + ;; and position have been highlighted, + ;; no need to highlight again. + (unless (eq imenu-default-goto-function + 'semantic-imenu-goto-function) + (helm-highlight-current-line))) + +(defun helm-imenu-persistent-action (candidate) + "Default persistent action for `helm-source-imenu'." + (helm-imenu--maybe-switch-to-buffer candidate) + (imenu candidate) + (helm-highlight-current-line)) + +(defun helm-imenu-candidates (&optional buffer) + (with-current-buffer (or buffer helm-current-buffer) + (let ((tick (buffer-modified-tick))) + (if (eq helm-cached-imenu-tick tick) + helm-cached-imenu-candidates + (setq imenu--index-alist nil) + (prog1 (setq helm-cached-imenu-candidates + (let ((index (imenu--make-index-alist t))) + (helm-imenu--candidates-1 + (delete (assoc "*Rescan*" index) index)))) + (setq helm-cached-imenu-tick tick)))))) + +(defun helm-imenu-candidates-in-all-buffers (&optional build-sources) + (let* ((lst (buffer-list)) + (progress-reporter (make-progress-reporter + "Imenu indexing buffers..." 1 (length lst)))) + (prog1 + (cl-loop with cur-buf = (if build-sources + (current-buffer) helm-current-buffer) + for b in lst + for count from 1 + when (with-current-buffer b + (and (or (member major-mode helm-imenu-extra-modes) + (derived-mode-p 'prog-mode)) + (helm-same-major-mode-p + cur-buf helm-imenu-all-buffer-assoc))) + if build-sources + collect (helm-make-source + (format "Imenu in %s" (buffer-name b)) + 'helm-imenu-source + :candidates (with-current-buffer b + (helm-imenu-candidates b)) + :fuzzy-match helm-imenu-fuzzy-match) + else + append (with-current-buffer b + (helm-imenu-candidates b)) + do (progress-reporter-update progress-reporter count)) + (progress-reporter-done progress-reporter)))) + +(defun helm-imenu--candidates-1 (alist) + (cl-loop for elm in alist + nconc (cond + ((imenu--subalist-p elm) + (helm-imenu--candidates-1 + (cl-loop for (e . v) in (cdr elm) collect + (cons (propertize + e 'helm-imenu-type (car elm)) + ;; If value is an integer, convert it + ;; to a marker, otherwise it is a cons cell + ;; and it will be converted on next recursions. + ;; (Issue #1060) [1]. + (if (integerp v) (copy-marker v) v))))) + ((listp (cdr elm)) + (and elm (list elm))) + (t + ;; bug in imenu, should not be needed. + (and (cdr elm) + ;; Semantic uses overlays whereas imenu uses + ;; markers (issue #1706). + (setcdr elm (pcase (cdr elm) ; Same as [1]. + ((and ov (pred overlayp)) + (copy-overlay ov)) + ((and mk (or (pred markerp) + (pred integerp))) + (copy-marker mk)))) + (list elm)))))) + +(defun helm-imenu--get-prop (item) + ;; property value of ITEM can have itself + ;; a property value which have itself a property value + ;; ...and so on; Return a list of all these + ;; properties values starting at ITEM. + (let* ((prop (get-text-property 0 'helm-imenu-type item)) + (lst (list prop item))) + (when prop + (while prop + (setq prop (get-text-property 0 'helm-imenu-type prop)) + (and prop (push prop lst))) + lst))) + +(defun helm-imenu-transformer (candidates) + (cl-loop for (k . v) in candidates + ;; (k . v) == (symbol-name . marker) + for bufname = (buffer-name + (pcase v + ((pred overlayp) (overlay-buffer v)) + ((or (pred markerp) (pred integerp)) + (marker-buffer v)))) + for types = (or (helm-imenu--get-prop k) + (list (if (with-current-buffer bufname + (derived-mode-p 'prog-mode)) + "Function" + "Top level") + k)) + for disp1 = (mapconcat + (lambda (x) + (propertize + x 'face + (cl-loop for (p . f) in helm-imenu-type-faces + when (string-match p x) return f + finally return 'default))) + types helm-imenu-delimiter) + for disp = (propertize disp1 'help-echo bufname 'types types) + collect + (cons disp (cons k v)))) + +;;;###autoload +(defun helm-imenu () + "Preconfigured `helm' for `imenu'." + (interactive) + (unless helm-source-imenu + (setq helm-source-imenu + (helm-make-source "Imenu" 'helm-imenu-source + :fuzzy-match helm-imenu-fuzzy-match))) + (let ((imenu-auto-rescan t) + (str (thing-at-point 'symbol)) + (helm-execute-action-at-once-if-one + helm-imenu-execute-action-at-once-if-one)) + (helm :sources 'helm-source-imenu + :default (list (concat "\\_<" (and str (regexp-quote str)) "\\_>") str) + :preselect str + :buffer "*helm imenu*"))) + +;;;###autoload +(defun helm-imenu-in-all-buffers () + "Preconfigured helm for fetching imenu entries in all buffers with similar mode as current. +A mode is similar as current if it is the same, it is derived i.e `derived-mode-p' +or it have an association in `helm-imenu-all-buffer-assoc'." + (interactive) + (unless helm-imenu-in-all-buffers-separate-sources + (unless helm-source-imenu-all + (setq helm-source-imenu-all + (helm-make-source "Imenu in all buffers" 'helm-imenu-source + :init (lambda () + ;; Use a cache to avoid repeatedly sending + ;; progress-reporter message when updating + ;; (Issue #1704). + (setq helm-imenu--in-all-buffers-cache + (helm-imenu-candidates-in-all-buffers))) + :candidates 'helm-imenu--in-all-buffers-cache + :fuzzy-match helm-imenu-fuzzy-match)))) + (let ((imenu-auto-rescan t) + (str (thing-at-point 'symbol)) + (helm-execute-action-at-once-if-one + helm-imenu-execute-action-at-once-if-one) + (helm--maybe-use-default-as-input + (not (null (memq 'helm-source-imenu-all + helm-sources-using-default-as-input)))) + (sources (if helm-imenu-in-all-buffers-separate-sources + (helm-imenu-candidates-in-all-buffers 'build-sources) + '(helm-source-imenu-all)))) + (helm :sources sources + :default (list (concat "\\_<" (and str (regexp-quote str)) "\\_>") str) + :preselect (unless helm--maybe-use-default-as-input str) + :buffer "*helm imenu all*"))) + +(provide 'helm-imenu) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-imenu.el ends here diff --git a/elpa/helm-20191031.839/helm-info.el b/elpa/helm-20191031.839/helm-info.el new file mode 100644 index 00000000..c484ab6c --- /dev/null +++ b/elpa/helm-20191031.839/helm-info.el @@ -0,0 +1,268 @@ +;;; helm-info.el --- Browse info index with helm -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'cl-lib) +(require 'helm) +(require 'helm-lib) +(require 'helm-utils) +(require 'info) + +(declare-function Info-index-nodes "info" (&optional file)) +(declare-function Info-goto-node "info" (&optional fork)) +(declare-function Info-find-node "info.el" (filename nodename &optional no-going-back)) +(defvar Info-history) +(defvar Info-directory-list) + +;;; Customize + +(defgroup helm-info nil + "Info-related applications and libraries for Helm." + :group 'helm) + +(defcustom helm-info-default-sources + '(helm-source-info-elisp + helm-source-info-cl + helm-source-info-eieio + helm-source-info-pages) + "Default sources to use for looking up symbols at point in Info +files with `helm-info-at-point'." + :group 'helm-info + :type '(repeat (choice symbol))) + +;;; Build info-index sources with `helm-info-source' class. + +(cl-defun helm-info-init (&optional (file (helm-attr 'info-file))) + ;; Allow reinit candidate buffer when using edebug. + (helm-aif (and debug-on-error + (helm-candidate-buffer)) + (kill-buffer it)) + (unless (helm-candidate-buffer) + (save-selected-window + (info file " *helm info temp buffer*") + (let ((tobuf (helm-candidate-buffer 'global)) + Info-history + start end line) + (cl-dolist (node (Info-index-nodes)) + (Info-goto-node node) + (goto-char (point-min)) + (while (search-forward "\n* " nil t) + (unless (search-forward "Menu:\n" (1+ (point-at-eol)) t) + (setq start (point-at-bol) + ;; Fix issue #1503 by getting the invisible + ;; info displayed on next line in long strings. + ;; e.g "* Foo.\n (line 12)" instead of + ;; "* Foo.(line 12)" + end (or (save-excursion + (goto-char (point-at-bol)) + (re-search-forward "(line +[0-9]+)" nil t)) + (point-at-eol)) + ;; Long string have a new line inserted before the + ;; invisible spec, remove it. + line (replace-regexp-in-string + "\n" "" (buffer-substring start end))) + (with-current-buffer tobuf + (insert line) + (insert "\n"))))) + (bury-buffer))))) + +(defun helm-info-goto (node-line) + (Info-goto-node (car node-line)) + (helm-goto-line (cdr node-line))) + +(defun helm-info-display-to-real (line) + (and (string-match + ;; This regexp is stolen from Info-apropos-matches + "\\* +\\([^\n]*.+[^\n]*\\):[ \t]+\\([^\n]*\\)\\.\\(?:[ \t\n]*(line +\\([0-9]+\\))\\)?" line) + (cons (format "(%s)%s" (helm-attr 'info-file) (match-string 2 line)) + (string-to-number (or (match-string 3 line) "1"))))) + +(defclass helm-info-source (helm-source-in-buffer) + ((info-file :initarg :info-file + :initform nil + :custom 'string) + (init :initform #'helm-info-init) + (display-to-real :initform #'helm-info-display-to-real) + (get-line :initform #'buffer-substring) + (action :initform '(("Goto node" . helm-info-goto))))) + +(defmacro helm-build-info-source (fname &rest args) + `(helm-make-source (concat "Info Index: " ,fname) 'helm-info-source + :info-file ,fname ,@args)) + +(defun helm-build-info-index-command (name doc source buffer) + "Define a helm command NAME with documentation DOC. +Arg SOURCE will be an existing helm source named +`helm-source-info-' and BUFFER a string buffer name." + (defalias (intern (concat "helm-info-" name)) + (lambda () + (interactive) + (helm :sources source + :buffer buffer + :candidate-number-limit 1000)) + doc)) + +(defun helm-define-info-index-sources (var-value &optional commands) + "Define helm sources named helm-source-info-. +Sources are generated for all entries of `helm-default-info-index-list'. +If COMMANDS arg is non-nil, also build commands named `helm-info-'. +Where NAME is an element of `helm-default-info-index-list'." + (cl-loop for str in var-value + for sym = (intern (concat "helm-source-info-" str)) + do (set sym (helm-build-info-source str)) + when commands + do (helm-build-info-index-command + str (format "Predefined helm for %s info." str) + sym (format "*helm info %s*" str)))) + +(defun helm-info-index-set (var value) + (set var value) + (helm-define-info-index-sources value t)) + +;;; Search Info files + +;; `helm-info' is the main entry point here. It prompts the user for an Info +;; file, then a term in the file's index to jump to. + +(defvar helm-info-searched (make-ring 32) + "Ring of previously searched Info files.") + +(defun helm-get-info-files () + "Return list of Info files to use for `helm-info'. + +Elements of the list are strings of Info file names without +extensions (e.g. \"emacs\" for file \"emacs.info.gz\"). Info +files are found by searching directories in +`Info-directory-list'." + (info-initialize) ; Build Info-directory-list from INFOPATH (Issue #2118) + (let ((files (cl-loop for d in (or Info-directory-list + Info-default-directory-list) + when (file-directory-p d) + append (directory-files d nil "\\.info")))) + (helm-fast-remove-dups + (cl-loop for f in files collect + (helm-file-name-sans-extension f)) + :test 'equal))) + +(defcustom helm-default-info-index-list + (helm-get-info-files) + "Info files to search in with `helm-info'." + :group 'helm-info + :type '(repeat (choice string)) + :set 'helm-info-index-set) + +(defun helm-info-search-index (candidate) + "Search the index of CANDIDATE's Info file using the function +helm-info-." + (let ((helm-info-function + (intern-soft (concat "helm-info-" candidate)))) + (when (fboundp helm-info-function) + (funcall helm-info-function) + (ring-insert helm-info-searched candidate)))) + +(defun helm-def-source--info-files () + "Return a `helm' source for Info files." + (helm-build-sync-source "Helm Info" + :candidates + (lambda () (copy-sequence helm-default-info-index-list)) + :candidate-number-limit 999 + :candidate-transformer + (lambda (candidates) + (sort candidates #'string-lessp)) + :nomark t + :action '(("Search index" . helm-info-search-index)))) + +;;;###autoload +(defun helm-info (&optional refresh) + "Preconfigured `helm' for searching Info files' indices. + +With a prefix argument \\[universal-argument], set REFRESH to non-nil. + +Optional parameter REFRESH, when non-nil, reevaluates +`helm-default-info-index-list'. If the variable has been +customized, set it to its saved value. If not, set it to its +standard value. See `custom-reevaluate-setting' for more. + +REFRESH is useful when new Info files are installed. If +`helm-default-info-index-list' has not been customized, the new +Info files are made available." + (interactive "P") + (let ((default (unless (ring-empty-p helm-info-searched) + (ring-ref helm-info-searched 0)))) + (when refresh + (custom-reevaluate-setting 'helm-default-info-index-list)) + (helm :sources (helm-def-source--info-files) + :buffer "*helm Info*" + :preselect (and default + (concat "\\_<" (regexp-quote default) "\\_>"))))) + +;;;; Info at point + +;; `helm-info-at-point' is the main entry point here. It searches for the +;; symbol at point through the Info sources defined in +;; `helm-info-default-sources' and jumps to it. + +(defvar helm-info--pages-cache nil + "Cache for all Info pages on the system.") + +(defvar helm-source-info-pages + (helm-build-sync-source "Info Pages" + :init #'helm-info-pages-init + :candidates (lambda () helm-info--pages-cache) + :action '(("Show with Info" . + (lambda (node-str) + (info (replace-regexp-in-string + "^[^:]+: " "" node-str))))) + :requires-pattern 2) + "Helm source for Info pages.") + +(defun helm-info-pages-init () + "Collect candidates for initial Info node Top." + (or helm-info--pages-cache + (let ((info-topic-regexp "\\* +\\([^:]+: ([^)]+)[^.]*\\)\\.")) + (save-selected-window + (info "dir" " *helm info temp buffer*") + (Info-find-node "dir" "top") + (goto-char (point-min)) + (while (re-search-forward info-topic-regexp nil t) + (push (match-string-no-properties 1) + helm-info--pages-cache)) + (kill-buffer))))) + +;;;###autoload +(defun helm-info-at-point () + "Preconfigured `helm' for searching info at point." + (interactive) + (cl-loop for src in helm-info-default-sources + for name = (if (symbolp src) + (assoc 'name (symbol-value src)) + (assoc 'name src)) + unless name + do (warn "Couldn't build source `%S' without its info file" src)) + (helm :sources helm-info-default-sources + :buffer "*helm info*")) + +(provide 'helm-info) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-info.el ends here diff --git a/elpa/helm-20191031.839/helm-locate.el b/elpa/helm-20191031.839/helm-locate.el new file mode 100644 index 00000000..ecba5cd5 --- /dev/null +++ b/elpa/helm-20191031.839/helm-locate.el @@ -0,0 +1,469 @@ +;;; helm-locate.el --- helm interface for locate. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;; NOTE for WINDOZE users: +;; You have to install Everything with his command line interface here: +;; http://www.voidtools.com/download.php + +;;; Code: + +(require 'cl-lib) +(require 'helm) +(require 'helm-types) +(require 'helm-help) + + +(defgroup helm-locate nil + "Locate related Applications and libraries for Helm." + :group 'helm) + +(defcustom helm-locate-db-file-regexp "m?locate\.db$" + "Default regexp to match locate database. +If nil Search in all files." + :type 'string + :group 'helm-locate) + +(defcustom helm-ff-locate-db-filename "locate.db" + "The basename of the locatedb file you use locally in your directories. +When this is set and `helm' find such a file in the directory from +where you launch locate, it will use this file and will not prompt you +for a db file. +Note that this happen only when locate is launched with a prefix arg." + :group 'helm-locate + :type 'string) + +(defcustom helm-locate-command nil + "A list of arguments for locate program. + +Helm will calculate a default value for your system on startup unless +`helm-locate-command' is non-nil, here the default values it will use +according to your system: + +Gnu/linux: \"locate %s -e -A --regex %s\" +berkeley-unix: \"locate %s %s\" +windows-nt: \"es %s %s\" +Others: \"locate %s %s\" + +This string will be passed to format so it should end with `%s'. +The first format spec is used for the \"-i\" value of locate/es, +So don't set it directly but use `helm-locate-case-fold-search' +for this. + +The last option must be the one preceding pattern i.e \"-r\" or \"--regex\". + +You will be able to pass other options such as \"-b\" or \"l\" +during helm invocation after entering pattern only when multi matching, +not when fuzzy matching. + +Note that the \"-b\" option is added automatically by helm when +var `helm-locate-fuzzy-match' is non-nil and switching back from +multimatch to fuzzy matching (this is done automatically when a space +is detected in pattern)." + :type 'string + :group 'helm-locate) + +(defcustom helm-locate-create-db-command + "updatedb -l 0 -o '%s' -U '%s'" + "Command used to create a locale locate db file." + :type 'string + :group 'helm-locate) + +(defcustom helm-locate-case-fold-search helm-case-fold-search + "It have the same meaning as `helm-case-fold-search'. +The -i option of locate will be used depending of value of +`helm-pattern' when this is set to 'smart. +When nil \"-i\" will not be used at all. +and when non--nil it will always be used. +NOTE: the -i option of the \"es\" command used on windows does +the opposite of \"locate\" command." + :group 'helm-locate + :type 'symbol) + +(defcustom helm-locate-fuzzy-match nil + "Enable fuzzy matching in `helm-locate'. +Note that when this is enabled searching is done on basename." + :group 'helm-locate + :type 'boolean) + +(defcustom helm-locate-fuzzy-sort-fn + #'helm-locate-default-fuzzy-sort-fn + "Default fuzzy matching sort function for locate." + :group 'helm-locate + :type 'boolean) + +(defcustom helm-locate-project-list nil + "A list of directories, your projects. +When set, allow browsing recursively files in all +directories of this list with `helm-projects-find-files'." + :group 'helm-locate + :type '(repeat string)) + +(defcustom helm-locate-recursive-dirs-command "locate -i -e -A --regex '^%s' '%s.*$'" + "Command used for recursive directories completion in `helm-find-files'. + +For Windows and `es' use something like \"es -r ^%s.*%s.*$\" + +The two format specs are mandatory. + +If for some reasons you can't use locate because your filesystem +doesn't have a data base, you can use find command from findutils but +be aware that it will be much slower, see `helm-find-files' embebded +help for more infos." + :type 'string + :group 'helm-files) + + +(defvar helm-locate-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-generic-files-map) + (define-key map (kbd "DEL") 'helm-delete-backward-no-update) + map)) + +(defface helm-locate-finish + '((t (:foreground "Green"))) + "Face used in mode line when locate process is finish." + :group 'helm-locate) + + +(defun helm-ff-find-locatedb (&optional from-ff) + "Try to find if a local locatedb file is available. +The search is done in `helm-ff-default-directory' or +fall back to `default-directory' if FROM-FF is nil." + (helm-aif (and helm-ff-locate-db-filename + (locate-dominating-file + (or (and from-ff + helm-ff-default-directory) + default-directory) + helm-ff-locate-db-filename)) + (expand-file-name helm-ff-locate-db-filename it))) + +(defun helm-locate-create-db-default-function (db-name directory) + "Default function used to create a locale locate db file. +Argument DB-NAME name of the db file. +Argument DIRECTORY root of file system subtree to scan." + (format helm-locate-create-db-command + db-name (expand-file-name directory))) + +(defvar helm-locate-create-db-function + #'helm-locate-create-db-default-function + "Function used to create a locale locate db file. +It should receive the same arguments as +`helm-locate-create-db-default-function'.") + +(defun helm-locate-1 (&optional localdb init from-ff default) + "Generic function to run Locate. +Prefix arg LOCALDB when (4) search and use a local locate db file when it +exists or create it, when (16) force update of existing db file +even if exists. +It have no effect when locate command is 'es'. +INIT is a string to use as initial input in prompt. +See `helm-locate-with-db' and `helm-locate'." + (require 'helm-mode) + (helm-locate-set-command) + (let ((pfn (lambda (candidate) + (if (file-directory-p candidate) + (message "Error: The locate Db should be a file") + (if (= (shell-command + (funcall helm-locate-create-db-function + candidate + helm-ff-default-directory)) + 0) + (message "New locatedb file `%s' created" candidate) + (error "Failed to create locatedb file `%s'" candidate))))) + (locdb (and localdb + (not (string-match "^es" helm-locate-command)) + (or (and (equal '(4) localdb) + (helm-ff-find-locatedb from-ff)) + (helm-read-file-name + "Create Locate Db file: " + :initial-input (expand-file-name "locate.db" + (or helm-ff-default-directory + default-directory)) + :preselect helm-locate-db-file-regexp + :test (lambda (x) + (if helm-locate-db-file-regexp + ;; Select only locate db files and directories + ;; to allow navigation. + (or (string-match + helm-locate-db-file-regexp x) + (file-directory-p x)) + x))))))) + (when (and locdb (or (equal localdb '(16)) + (not (file-exists-p locdb)))) + (funcall pfn locdb)) + (helm-locate-with-db (and localdb locdb) init default))) + +(defun helm-locate-set-command () + "Setup `helm-locate-command' if not already defined." + (unless helm-locate-command + (setq helm-locate-command + (cl-case system-type + (gnu/linux "locate %s -e -A --regex %s") + (berkeley-unix "locate %s %s") + (windows-nt "es %s %s") + (t "locate %s %s"))))) + +(defun helm-locate-initial-setup () + (require 'helm-for-files) + (helm-locate-set-command)) + +(defvar helm-file-name-history nil) +(defun helm-locate-with-db (&optional db initial-input default) + "Run locate -d DB. +If DB is not given or nil use locate without -d option. +Argument DB can be given as a string or list of db files. +Argument INITIAL-INPUT is a string to use as initial-input. +See also `helm-locate'." + (require 'helm-files) + (when (and db (stringp db)) (setq db (list db))) + (helm-locate-set-command) + (let ((helm-locate-command + (if db + (replace-regexp-in-string + "locate" + (format (if helm-locate-fuzzy-match + "locate -b -d '%s'" "locate -d '%s'") + (mapconcat 'identity + ;; Remove eventually + ;; marked directories by error. + (cl-loop for i in db + unless (file-directory-p i) + ;; expand-file-name to resolve + ;; abbreviated fnames not + ;; expanding inside single + ;; quotes i.e. '%s'. + collect (expand-file-name i)) + ":")) + helm-locate-command) + (if (and helm-locate-fuzzy-match + (not (string-match-p "\\`locate -b" helm-locate-command))) + (replace-regexp-in-string + "\\`locate" "locate -b" helm-locate-command) + helm-locate-command)))) + (setq helm-file-name-history (mapcar 'helm-basename file-name-history)) + (helm :sources 'helm-source-locate + :buffer "*helm locate*" + :ff-transformer-show-only-basename nil + :input initial-input + :default default + :history 'helm-file-name-history))) + +(defun helm-locate-update-mode-line (process-name) + "Update mode-line with PROCESS-NAME status information." + (with-helm-window + (setq mode-line-format + `(" " mode-line-buffer-identification " " + (:eval (format "L%s" (helm-candidate-number-at-point))) " " + (:eval (propertize + (format "[%s process finished - (%s results)]" + (max (1- (count-lines + (point-min) (point-max))) + 0) + ,process-name) + 'face 'helm-locate-finish)))) + (force-mode-line-update))) + +(defun helm-locate-init () + "Initialize async locate process for `helm-source-locate'." + (let* ((locate-is-es (string-match "\\`es" helm-locate-command)) + (real-locate (string-match "\\`locate" helm-locate-command)) + (case-sensitive-flag (if locate-is-es "-i" "")) + (ignore-case-flag (if (or locate-is-es + (not real-locate)) "" "-i")) + (args (helm-mm-split-pattern helm-pattern)) + (cmd (format helm-locate-command + (cl-case helm-locate-case-fold-search + (smart (let ((case-fold-search nil)) + (if (string-match "[[:upper:]]" helm-pattern) + case-sensitive-flag + ignore-case-flag))) + (t (if helm-locate-case-fold-search + ignore-case-flag + case-sensitive-flag))) + (concat + ;; The pattern itself. + (shell-quote-argument (car args)) " " + ;; Possible locate args added + ;; after pattern, don't quote them. + (mapconcat 'identity (cdr args) " ")))) + (default-directory (if (file-directory-p default-directory) + default-directory "/"))) + (helm-log "Starting helm-locate process") + (helm-log "Command line used was:\n\n%s" + (concat ">>> " (propertize cmd 'face 'font-lock-comment-face) "\n\n")) + (prog1 + (start-process-shell-command + "locate-process" helm-buffer + cmd) + (set-process-sentinel + (get-buffer-process helm-buffer) + (lambda (process event) + (let* ((err (process-exit-status process)) + (noresult (= err 1))) + (cond (noresult + (with-helm-buffer + (unless (cdr helm-sources) + (insert (concat "* Exit with code 1, no result found," + " command line was:\n\n " + cmd))))) + ((string= event "finished\n") + (when (and helm-locate-fuzzy-match + (not (string-match-p "\\s-" helm-pattern))) + (helm-redisplay-buffer)) + (helm-locate-update-mode-line "Locate")) + (t + (helm-log "Error: Locate %s" + (replace-regexp-in-string "\n" "" event)))))))))) + +(defun helm-locate-default-fuzzy-sort-fn (candidates) + "Default sort function for files in fuzzy matching. +Sort is done on basename of CANDIDATES." + (helm-fuzzy-matching-default-sort-fn-1 candidates nil t)) + +(defclass helm-locate-override-inheritor (helm-type-file) ()) + +(defclass helm-locate-source (helm-source-async helm-locate-override-inheritor) + ((init :initform 'helm-locate-initial-setup) + (candidates-process :initform 'helm-locate-init) + (requires-pattern :initform 3) + (history :initform 'helm-file-name-history) + (persistent-action :initform 'helm-ff-kill-or-find-buffer-fname) + (candidate-number-limit :initform 9999) + (redisplay :initform (progn helm-locate-fuzzy-sort-fn)) + (group :initform 'helm-locate))) + +;; Override helm-type-file class keymap. +(defmethod helm--setup-source :after ((source helm-locate-override-inheritor)) + (setf (slot-value source 'keymap) helm-locate-map)) + +(defvar helm-source-locate + (helm-make-source "Locate" 'helm-locate-source + :pattern-transformer 'helm-locate-pattern-transformer + ;; :match-part is only used here to tell helm which part + ;; of candidate to highlight. + :match-part (lambda (candidate) + (if (or (string-match-p " -b\\'" helm-pattern) + (and helm-locate-fuzzy-match + (not (string-match "\\s-" helm-pattern)))) + (helm-basename candidate) + candidate)))) + +(defun helm-locate-pattern-transformer (pattern) + (if helm-locate-fuzzy-match + ;; When fuzzy is enabled helm add "-b" option on startup. + (cond ((string-match-p " " pattern) + (when (string-match "\\`locate -b" helm-locate-command) + (setq helm-locate-command + (replace-match "locate" t t helm-locate-command))) + pattern) + (t + (unless (string-match-p "\\`locate -b" helm-locate-command) + (setq helm-locate-command + (replace-regexp-in-string + "\\`locate" "locate -b" helm-locate-command))) + (helm--mapconcat-pattern pattern))) + pattern)) + +(defun helm-locate-find-dbs-in-projects (&optional update) + (let* ((pfn (lambda (candidate directory) + (unless (= (shell-command + (funcall helm-locate-create-db-function + candidate + directory)) + 0) + (error "Failed to create locatedb file `%s'" candidate))))) + (cl-loop for p in helm-locate-project-list + for db = (expand-file-name + helm-ff-locate-db-filename + (file-name-as-directory p)) + if (and (null update) (file-exists-p db)) + collect db + else do (funcall pfn db p) + and collect db))) + +;;; Directory completion for hff. +;; +(defclass helm-locate-subdirs-source (helm-source-in-buffer) + ((basedir :initarg :basedir + :initform nil + :custom string) + (subdir :initarg :subdir + :initform nil + :custom 'string) + (data :initform #'helm-locate-init-subdirs) + (group :initform 'helm-locate))) + +(defun helm-locate-init-subdirs () + (with-temp-buffer + (call-process-shell-command + (format helm-locate-recursive-dirs-command + (if (string-match-p "\\`es" helm-locate-recursive-dirs-command) + ;; Fix W32 paths. + (replace-regexp-in-string + "/" "\\\\\\\\" (helm-attr 'basedir)) + (helm-attr 'basedir)) + (helm-attr 'subdir)) + nil t nil) + (buffer-string))) + +;;;###autoload +(defun helm-projects-find-files (update) + "Find files with locate in `helm-locate-project-list'. +With a prefix arg refresh the database in each project." + (interactive "P") + (helm-locate-set-command) + (cl-assert (and (string-match-p "\\`locate" helm-locate-command) + (executable-find "updatedb")) + nil "Unsupported locate version") + (let ((dbs (helm-locate-find-dbs-in-projects update))) + (if dbs + (helm-locate-with-db dbs) + (user-error "No projects found, please setup `helm-locate-project-list'")))) + +;;;###autoload +(defun helm-locate (arg) + "Preconfigured `helm' for Locate. +Note: you can add locate options after entering pattern. +See 'man locate' for valid options and also `helm-locate-command'. + +You can specify a local database with prefix argument ARG. +With two prefix arg, refresh the current local db or create it +if it doesn't exists. + +To create a user specific db, use +\"updatedb -l 0 -o db_path -U directory\". +Where db_path is a filename matched by +`helm-locate-db-file-regexp'." + (interactive "P") + (helm-set-local-variable 'helm-async-outer-limit-hook + (list (lambda () + (when (and helm-locate-fuzzy-match + (not (string-match-p + "\\s-" helm-pattern))) + (helm-redisplay-buffer))))) + (setq helm-ff-default-directory default-directory) + (helm-locate-1 arg nil nil (thing-at-point 'filename))) + +(provide 'helm-locate) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-locate.el ends here diff --git a/elpa/helm-20191031.839/helm-man.el b/elpa/helm-20191031.839/helm-man.el new file mode 100644 index 00000000..26f8135f --- /dev/null +++ b/elpa/helm-20191031.839/helm-man.el @@ -0,0 +1,119 @@ +;;; helm-man.el --- Man and woman UI -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'cl-lib) +(require 'helm) +(require 'helm-help) + +(defvar woman-topic-all-completions) +(defvar woman-manpath) +(defvar woman-path) +(defvar woman-expanded-directory-path) +(declare-function woman-file-name "woman.el" (topic &optional re-cache)) +(declare-function woman-file-name-all-completions "woman.el" (topic)) +(declare-function Man-getpage-in-background "man.el" (topic)) +(declare-function woman-expand-directory-path "woman.el" (path-dirs path-regexps)) +(declare-function woman-topic-all-completions "woman.el" (path)) +(declare-function helm-generic-sort-fn "helm-utils.el" (S1 S2)) + +(defgroup helm-man nil + "Man and Woman applications for helm." + :group 'helm) + +(defcustom helm-man-or-woman-function 'Man-getpage-in-background + "Default command to display a man page." + :group 'helm-man + :type '(radio :tag "Preferred command to display a man page" + (const :tag "Man" Man-getpage-in-background) + (const :tag "Woman" woman))) + +(defcustom helm-man-format-switches (cl-case system-type + ((darwin macos) "%s") + (t "-l %s")) + "Arguments to pass to the `manual-entry' function. +Arguments are passed to `manual-entry' with `format.'" + :group 'helm-man + :type 'string) + +;; Internal +(defvar helm-man--pages nil + "All man pages on system. +Will be calculated the first time you invoke helm with this +source.") + +(defun helm-man-default-action (candidate) + "Default action for jumping to a woman or man page from helm." + (let ((wfiles (mapcar #'car (woman-file-name-all-completions candidate)))) + (condition-case nil + (let ((file (if (cdr wfiles) + (helm-comp-read "ManFile: " wfiles :must-match t) + (car wfiles)))) + (if (eq helm-man-or-woman-function 'Man-getpage-in-background) + (manual-entry (format helm-man-format-switches file)) + (condition-case nil + (woman-find-file file) + ;; If woman is unable to format correctly + ;; try Man instead. + (error (kill-buffer) + (manual-entry (format helm-man-format-switches file)))))) + ;; If even Man failed with file as argument, try again with Man + ;; but using Topic candidate instead of the file calculated by + ;; woman. + (error (kill-buffer) + (Man-getpage-in-background candidate))))) + +(defun helm-man--init () + (require 'woman) + (require 'helm-utils) + (unless helm-man--pages + (setq woman-expanded-directory-path + (woman-expand-directory-path woman-manpath woman-path)) + (setq woman-topic-all-completions + (woman-topic-all-completions woman-expanded-directory-path)) + (setq helm-man--pages (mapcar 'car woman-topic-all-completions))) + (helm-init-candidates-in-buffer 'global helm-man--pages)) + +(defvar helm-source-man-pages + (helm-build-in-buffer-source "Manual Pages" + :init #'helm-man--init + :persistent-action #'ignore + :filtered-candidate-transformer + (lambda (candidates _source) + (sort candidates #'helm-generic-sort-fn)) + :action '(("Display Man page" . helm-man-default-action)) + :group 'helm-man)) + +;;;###autoload +(defun helm-man-woman (arg) + "Preconfigured `helm' for Man and Woman pages. +With a prefix arg reinitialize the cache." + (interactive "P") + (when arg (setq helm-man--pages nil)) + (helm :sources 'helm-source-man-pages + :buffer "*helm man woman*")) + +(provide 'helm-man) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-man.el ends here diff --git a/elpa/helm-20191031.839/helm-misc.el b/elpa/helm-20191031.839/helm-misc.el new file mode 100644 index 00000000..7843f0fb --- /dev/null +++ b/elpa/helm-20191031.839/helm-misc.el @@ -0,0 +1,333 @@ +;;; helm-misc.el --- Various functions for helm -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: +(require 'cl-lib) +(require 'helm) +(require 'helm-help) +(require 'helm-types) + +(declare-function display-time-world-display "time.el") +(defvar display-time-world-list) +(declare-function LaTeX-math-mode "ext:latex.el") +(declare-function jabber-chat-with "ext:jabber.el") +(declare-function jabber-read-account "ext:jabber.el") + + +(defgroup helm-misc nil + "Various Applications and libraries for Helm." + :group 'helm) + +(defcustom helm-time-zone-home-location "Paris" + "The time zone of your home" + :group 'helm-misc + :type 'string) + +(defcustom helm-timezone-actions + '(("Set timezone env (TZ)" . (lambda (candidate) + (setenv "TZ" candidate)))) + "Actions for helm-timezone." + :group 'helm-misc + :type '(alist :key-type string :value-type function)) + +(defface helm-time-zone-current + '((t (:foreground "green"))) + "Face used to colorize current time in `helm-world-time'." + :group 'helm-misc) + +(defface helm-time-zone-home + '((t (:foreground "red"))) + "Face used to colorize home time in `helm-world-time'." + :group 'helm-misc) + + + +;;; Latex completion +;; +;; Test +;; (setq LaTeX-math-menu '("Math" +;; ["foo" val0 t] +;; ("bar" +;; ["baz" val1 t]) +;; ("aze" +;; ["zer" val2 t]) +;; ("AMS" +;; ("rec" +;; ["fer" val3 t]) +;; ("rty" +;; ["der" val4 t])) +;; ("ABC" +;; ("xcv" +;; ["sdf" val5 t]) +;; ("dfg" +;; ["fgh" val6 t])))) +;; (helm-latex-math-candidates) +;; => +;; (("foo" . val0) +;; ("baz" . val1) +;; ("zer" . val2) +;; ("fer" . val3) +;; ("der" . val4) +;; ("sdf" . val5) +;; ("fgh" . val6)) + +(defvar LaTeX-math-menu) +(defun helm-latex-math-candidates () + (cl-labels ((helm-latex--math-collect (L) + (cond ((vectorp L) + (list (cons (aref L 0) (aref L 1)))) + ((listp L) + (cl-loop for a in L nconc + (helm-latex--math-collect a)))))) + (helm-latex--math-collect LaTeX-math-menu))) + +(defvar helm-source-latex-math + (helm-build-sync-source "Latex Math Menu" + :init (lambda () + (with-helm-current-buffer + (LaTeX-math-mode 1))) + :candidate-number-limit 9999 + :candidates 'helm-latex-math-candidates + :action (lambda (candidate) + (call-interactively candidate)))) + + +;;; Jabber Contacts (jabber.el) +(defun helm-jabber-online-contacts () + "List online Jabber contacts." + (with-no-warnings + (cl-loop for item in (jabber-concat-rosters) + when (get item 'connected) + collect + (if (get item 'name) + (cons (get item 'name) item) + (cons (symbol-name item) item))))) + +(defvar helm-source-jabber-contacts + (helm-build-sync-source "Jabber Contacts" + :init (lambda () (require 'jabber)) + :candidates (lambda () (mapcar 'car (helm-jabber-online-contacts))) + :action (lambda (x) + (jabber-chat-with + (jabber-read-account) + (symbol-name + (cdr (assoc x (helm-jabber-online-contacts)))))))) + +;;; World time +;; +(defvar zoneinfo-style-world-list) +(defvar legacy-style-world-list) + +(defun helm-time-zone-transformer (candidates _source) + (cl-loop for i in candidates + for (z . p) in display-time-world-list + collect + (cons + (cond ((string-match (format-time-string "%H:%M" (current-time)) i) + (propertize i 'face 'helm-time-zone-current)) + ((string-match helm-time-zone-home-location i) + (propertize i 'face 'helm-time-zone-home)) + (t i)) + z))) + +(defvar helm-source-time-world + (helm-build-in-buffer-source "Time World List" + :init (lambda () + (require 'time) + (unless (and display-time-world-list + (listp display-time-world-list)) + ;; adapted from `time--display-world-list' from + ;; emacs-27 for compatibility as + ;; `display-time-world-list' is set by default to t. + (setq display-time-world-list + ;; Determine if zoneinfo style timezones are + ;; supported by testing that America/New York and + ;; Europe/London return different timezones. + (let ((nyt (format-time-string "%z" nil "America/New_York")) + (gmt (format-time-string "%z" nil "Europe/London"))) + (if (string-equal nyt gmt) + legacy-style-world-list + zoneinfo-style-world-list))))) + :data (lambda () + (with-temp-buffer + (display-time-world-display display-time-world-list) + (buffer-string))) + :action 'helm-timezone-actions + :filtered-candidate-transformer 'helm-time-zone-transformer)) + +;;; Commands +;; +(defun helm-call-interactively (cmd-or-name) + "Execute CMD-OR-NAME as Emacs command. +It is added to `extended-command-history'. +`helm-current-prefix-arg' is used as the command's prefix argument." + (setq extended-command-history + (cons (helm-stringify cmd-or-name) + (delete (helm-stringify cmd-or-name) extended-command-history))) + (let ((current-prefix-arg helm-current-prefix-arg) + (cmd (helm-symbolify cmd-or-name))) + (if (stringp (symbol-function cmd)) + (execute-kbd-macro (symbol-function cmd)) + (setq this-command cmd) + (call-interactively cmd)))) + +;;; Minibuffer History +;; +;; +(defvar helm-minibuffer-history-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map [remap helm-minibuffer-history] 'undefined) + map)) + +(defcustom helm-minibuffer-history-must-match t + "Allow inserting non matching elements when nil or 'confirm." + :group 'helm-misc + :type '(choice + (const :tag "Must match" t) + (const :tag "Confirm" 'confirm) + (const :tag "Always allow" nil))) + + +;;; Helm ratpoison UI +;; +;; +(defvar helm-source-ratpoison-commands + (helm-build-in-buffer-source "Ratpoison Commands" + :init 'helm-ratpoison-commands-init + :action (helm-make-actions + "Execute the command" 'helm-ratpoison-commands-execute) + :display-to-real 'helm-ratpoison-commands-display-to-real + :candidate-number-limit 999999)) + +(defun helm-ratpoison-commands-init () + (unless (helm-candidate-buffer) + (with-current-buffer (helm-candidate-buffer 'global) + ;; with ratpoison prefix key + (save-excursion + (call-process "ratpoison" nil (current-buffer) nil "-c" "help")) + (while (re-search-forward "^\\([^ ]+\\) \\(.+\\)$" nil t) + (replace-match " \\1: \\2")) + (goto-char (point-max)) + ;; direct binding + (save-excursion + (call-process "ratpoison" nil (current-buffer) nil "-c" "help top")) + (while (re-search-forward "^\\([^ ]+\\) \\(.+\\)$" nil t) + (replace-match "\\1: \\2"))))) + +(defun helm-ratpoison-commands-display-to-real (display) + (and (string-match ": " display) + (substring display (match-end 0)))) + +(defun helm-ratpoison-commands-execute (candidate) + (call-process "ratpoison" nil nil nil "-ic" candidate)) + +;;; Helm stumpwm UI +;; +;; +(defvar helm-source-stumpwm-commands + (helm-build-in-buffer-source "Stumpwm Commands" + :init 'helm-stumpwm-commands-init + :action (helm-make-actions + "Execute the command" 'helm-stumpwm-commands-execute) + :candidate-number-limit 999999)) + +(defun helm-stumpwm-commands-init () + (with-current-buffer (helm-candidate-buffer 'global) + (save-excursion + (call-process "stumpish" nil (current-buffer) nil "commands")) + (while (re-search-forward "[ ]*\\([^ ]+\\)[ ]*\n?" nil t) + (replace-match "\n\\1\n")) + (delete-blank-lines) + (sort-lines nil (point-min) (point-max)) + (goto-char (point-max)))) + +(defun helm-stumpwm-commands-execute (candidate) + (call-process "stumpish" nil nil nil candidate)) + +;;;###autoload +(defun helm-world-time () + "Preconfigured `helm' to show world time. +Default action change TZ environment variable locally to emacs." + (interactive) + (helm-other-buffer 'helm-source-time-world "*helm world time*")) + +;;;###autoload +(defun helm-insert-latex-math () + "Preconfigured helm for latex math symbols completion." + (interactive) + (helm-other-buffer 'helm-source-latex-math "*helm latex*")) + +;;;###autoload +(defun helm-ratpoison-commands () + "Preconfigured `helm' to execute ratpoison commands." + (interactive) + (helm-other-buffer 'helm-source-ratpoison-commands + "*helm ratpoison commands*")) + +;;;###autoload +(defun helm-stumpwm-commands() + "Preconfigured helm for stumpwm commands." + (interactive) + (helm-other-buffer 'helm-source-stumpwm-commands + "*helm stumpwm commands*")) + +;;;###autoload +(defun helm-minibuffer-history () + "Preconfigured `helm' for `minibuffer-history'." + (interactive) + (cl-assert (minibuffer-window-active-p (selected-window)) nil + "Error: Attempt to use minibuffer history outside a minibuffer") + (let* ((enable-recursive-minibuffers t) + (query-replace-p (or (eq last-command 'query-replace) + (eq last-command 'query-replace-regexp))) + (elm (helm-comp-read "pattern: " + (cl-loop for i in + (symbol-value minibuffer-history-variable) + unless (string= "" i) collect i into history + finally return + (if (consp (car history)) + (mapcar 'prin1-to-string history) + history)) + :header-name + (lambda (name) + (format "%s (%s)" name minibuffer-history-variable)) + :buffer "*helm minibuffer-history*" + :must-match helm-minibuffer-history-must-match + :multiline t + :keymap helm-minibuffer-history-map + :allow-nest t))) + ;; Fix issue #1667 with emacs-25+ `query-replace-from-to-separator'. + (when (and (boundp 'query-replace-from-to-separator) query-replace-p) + (let ((pos (string-match "\0" elm))) + (and pos + (add-text-properties + pos (1+ pos) + `(display ,query-replace-from-to-separator separator t) + elm)))) + (delete-minibuffer-contents) + (insert elm))) + +(provide 'helm-misc) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-misc.el ends here diff --git a/elpa/helm-20191031.839/helm-mode.el b/elpa/helm-20191031.839/helm-mode.el new file mode 100644 index 00000000..36521a4b --- /dev/null +++ b/elpa/helm-20191031.839/helm-mode.el @@ -0,0 +1,1727 @@ +;;; helm-mode.el --- Enable helm completion everywhere. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'cl-lib) +(require 'helm) +(require 'helm-lib) +(require 'helm-files) + +(defvar crm-separator) +(defvar ido-everywhere) +(declare-function ido-mode "ido.el") + +(defgroup helm-mode nil + "Enable helm completion." + :group 'helm) + +(defcustom helm-completing-read-handlers-alist + '((describe-function . helm-completing-read-symbols) + (describe-variable . helm-completing-read-symbols) + (describe-symbol . helm-completing-read-symbols) + (debug-on-entry . helm-completing-read-symbols) + (find-function . helm-completing-read-symbols) + (disassemble . helm-completing-read-symbols) + (trace-function . helm-completing-read-symbols) + (trace-function-foreground . helm-completing-read-symbols) + (trace-function-background . helm-completing-read-symbols) + (find-tag . helm-completing-read-default-find-tag) + (xref-find-definitions . helm-completing-read-default-find-tag) + (xref-find-references . helm-completing-read-default-find-tag) + (ffap-alternate-file . nil) + (tmm-menubar . nil) + (find-file . nil) + (find-file-at-point . helm-completing-read-sync-default-handler) + (ffap . helm-completing-read-sync-default-handler) + (execute-extended-command . nil) + (dired-do-rename . helm-read-file-name-handler-1) + (dired-do-copy . helm-read-file-name-handler-1) + (dired-do-symlink . helm-read-file-name-handler-1) + (dired-do-relsymlink . helm-read-file-name-handler-1) + (dired-do-hardlink . helm-read-file-name-handler-1) + (basic-save-buffer . helm-read-file-name-handler-1) + (write-file . helm-read-file-name-handler-1) + (write-region . helm-read-file-name-handler-1)) + "Completing read functions for specific Emacs commands. + +By default `helm-mode' use `helm-completing-read-default-handler' to +provide helm completion in each `completing-read' or `read-file-name' +found, but other functions can be specified here for specific +commands. This also allow disabling helm completion for some commands +when needed. + +Each entry is a cons cell like (EMACS_COMMAND . COMPLETING-READ_HANDLER) +where key and value are symbols. + +Each key is an Emacs command that use originaly `completing-read'. + +Each value maybe a helm function that takes same arguments as +`completing-read' plus NAME and BUFFER, where NAME is the name of the new +helm source and BUFFER the name of the buffer we will use, but it can +be also a function not using helm, in this case the function should +take same args as `completing-read' and not be prefixed by \"helm-\". + +`helm' will use the name of the command calling `completing-read' as +NAME and BUFFER will be computed as well with NAME but prefixed with +\"*helm-mode-\". + +This function prefix name must start by \"helm-\" when it uses helm, +otherwise `helm' assumes the function is not a helm function and +expects same args as `completing-read', this allow you to define a +handler not using helm completion. + +Example: + + (defun foo/test () + (interactive) + (message \"%S\" (completing-read \"test: \" '(a b c d e)))) + + (defun helm-foo/test-completing-read-handler (prompt collection + predicate require-match + initial-input hist def + inherit-input-method + name buffer) + (helm-comp-read prompt collection :marked-candidates t + :name name + :buffer buffer)) + + (add-to-list 'helm-completing-read-handlers-alist + '(foo/test . helm-foo/test-completing-read-handler)) + + +We want here to make the regular `completing-read' in `foo/test' +returns a list of candidate(s) instead of a single candidate. + +Note that this function will be reused for ALL the `completing-read' +of this command, so it should handle all cases, e.g +If first `completing-read' complete against symbols and +second `completing-read' should handle only buffer, +your specialized function should handle the both. + +If the value of an entry is nil completion will fall back to +emacs vanilla behavior. +Example: + +If you want to disable helm completion for `describe-function', use: + + (describe-function . nil) + +Ido is also supported, you can use `ido-completing-read' and +`ido-read-file-name' as value of an entry or just 'ido. +Example: +Enable ido completion for `find-file': + + (find-file . ido) + +same as + + (find-file . ido-read-file-name) + +Note that you don't need to enable `ido-mode' for this to work, see +`helm-mode' documentation." + :group 'helm-mode + :type '(alist :key-type symbol :value-type symbol)) + +(defcustom helm-comp-read-case-fold-search helm-case-fold-search + "Default Local setting of `helm-case-fold-search' for `helm-comp-read'. +See `helm-case-fold-search' for more info." + :group 'helm-mode + :type 'symbol) + +(defcustom helm-mode-handle-completion-in-region t + "Whether to replace or not `completion-in-region-function'. +This enable support for `completing-read-multiple' and `completion-at-point' +when non--nil." + :group 'helm-mode + :type 'boolean) + +(defcustom helm-mode-reverse-history t + "Display history source after current source in `helm-mode' handled commands." + :group 'helm-mode + :type 'boolean) + +(defcustom helm-mode-no-completion-in-region-in-modes nil + "A list of modes that do not want helm for `completion-in-region'." + :group 'helm-mode + :type 'boolean) + +(defcustom helm-completion-in-region-default-sort-fn + 'helm-completion-in-region-sort-fn + "The default sort function to sort candidates in completion-in-region. + +When nil no sorting is done. +The function is a `filtered-candidate-transformer' function which takes +two args CANDIDATES and SOURCE. +It will be used only when `helm-completion-style' is either emacs or +helm, otherwise when helm-fuzzy style is used, the fuzzy sort function +will be used." + :group 'helm-mode + :type 'function) + +(defcustom helm-mode-fuzzy-match nil + "Enable fuzzy matching in `helm-mode' globally. +Note that this will slow down completion and modify sorting +which is unwanted in many places. +This affect only the functions with completing-read helmized by helm-mode. +To fuzzy match `completion-at-point' and friends see +`helm-completion-style'." + :group 'helm-mode + :type 'boolean) + +(defcustom helm-mode-minibuffer-setup-hook-black-list '(minibuffer-completion-help) + "Incompatible `minibuffer-setup-hook' functions go here. +A list of symbols. +Helm-mode is rejecting all lambda's, byte-code fns +and all functions belonging in this list from `minibuffer-setup-hook'." + :group 'helm-mode + :type '(repeat (choice symbol))) + +(defcustom helm-completing-read-dynamic-complete nil + "Use dynamic completion in `completing-read' when non-nil. + +The default is to not use this because it is most of the time unneeded +in `completing-read' and thus it is much more slower. +If you feel one emacs function need this you have better time to tell +`helm-mode' to use a dynamic completion for this function only by using +`helm-completing-read-handlers-alist' with an entry like this: + + (my-function . helm-completing-read-sync-default-handler) + +So you should not change the default setting of this variable unless you +know what you are doing." + :group 'helm-mode + :type 'boolean) + +(defface helm-mode-prefix + '((t (:background "red" :foreground "black"))) + "Face used for prefix completion." + :group 'helm-mode) + +(defvar helm-comp-read-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "") 'helm-cr-empty-string) + (define-key map (kbd "M-RET") 'helm-cr-empty-string) + map) + "Keymap for `helm-comp-read'.") + +(defun helm-mode-delete-char-backward-1 () + (interactive) + (condition-case err + (call-interactively 'delete-backward-char) + (text-read-only + (if (with-selected-window (minibuffer-window) + (not (string= (minibuffer-contents) ""))) + (message "Trying to delete prefix completion, next hit will quit") + (user-error "%s" (car err)))))) +(put 'helm-mode-delete-char-backward-1 'helm-only t) + +(defun helm-mode-delete-char-backward-2 () + (interactive) + (condition-case _err + (call-interactively 'delete-backward-char) + (text-read-only + (unless (with-selected-window (minibuffer-window) + (string= (minibuffer-contents) "")) + (with-helm-current-buffer + (run-with-timer 0.1 nil (lambda () + (call-interactively 'delete-backward-char)))) + (helm-keyboard-quit))))) +(put 'helm-mode-delete-char-backward-2 'helm-only t) + +(helm-multi-key-defun helm-mode-delete-char-backward-maybe + "Delete char backward when text is not the prefix helm is completing against. +First call warn user about deleting prefix completion. +Second call delete backward char in current-buffer and quit helm completion, +letting user starting a new completion with a new prefix." + '(helm-mode-delete-char-backward-1 helm-mode-delete-char-backward-2) 1) + +(defcustom helm-completion-style 'emacs + "Style of completion to use in `completion-in-region'. + +This affect only `completion-at-point' and friends, NOT +`completing-read' nor other helm commands. + +NB: This have nothing to do with `completion-styles', it is independent to +helm. + +There is three possible value to use: +- helm, use multi match regular helm completion. +- helm-fuzzy, use fuzzy matching, note that as usual when + entering a space helm switch to multi matching mode. +- emacs, use regular emacs completion according to + `completion-styles', note that even in this style, helm allow using + multi match. Emacs-27 provide a style called flex that can be used + along this helm style (see `completion-styles-alist'). + +Please use custom interface or `customize-set-variable' to set this, +NOT `setq'." + :group 'helm-mode + :type '(choice (const :tag "Emacs" emacs) + (const :tag "Helm" helm) + (const :tag "Helm-fuzzy" helm-fuzzy)) + :set (lambda (var val) + (set var val) + (if (memq val '(helm helm-fuzzy)) + (define-key helm-comp-read-map (kbd "DEL") 'helm-mode-delete-char-backward-maybe) + (define-key helm-comp-read-map (kbd "DEL") 'delete-backward-char)))) + +(defcustom helm-completion-styles-alist '((eshell-mode . helm)) + "Allow configuring `helm-completion-style' per mode. + +Each entry is a cons cell like (mode . style) where style must be a +suitable value for `helm-completion-style'." + :group 'helm-mode + :type '(alist :key-type (symbol :tag "Mode") + :value-type (symbol :tag "Style"))) + +;;; helm-comp-read +;; +;; +(defun helm-cr-empty-string () + "Return empty string." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action + (lambda (_candidate) + (identity ""))))) +(put 'helm-cr-empty-string 'helm-only t) + +(defun helm-mode--keyboard-quit () + ;; Use this instead of `keyboard-quit' + ;; to avoid deactivating mark in current-buffer. + (let ((debug-on-quit nil)) + (signal 'quit nil))) + +(cl-defun helm-comp-read-get-candidates (collection &optional + test sort-fn alistp + (input helm-pattern)) + "Convert COLLECTION to list removing elements that don't match TEST. +See `helm-comp-read' about supported COLLECTION arguments. + +SORT-FN is a predicate to sort COLLECTION. + +ALISTP when non--nil will not use `all-completions' to collect +candidates because it doesn't handle alists correctly for helm. +i.e In `all-completions' the car of each pair is used as value. +In helm we want to use the cdr instead like \(display . real\), +so we return the alist as it is with no transformation by +`all-completions'. + +e.g + +\(setq A '((a . 1) (b . 2) (c . 3))) +==>((a . 1) (b . 2) (c . 3)) +\(helm-comp-read \"test: \" A :alistp nil + :exec-when-only-one t + :initial-input \"a\") +==>\"a\" Which is not what we expect. + +\(helm-comp-read \"test: \" A :alistp t + :exec-when-only-one t + :initial-input \"1\") +==>\"1\" + +See docstring of `all-completions' for more info. + +INPUT is the string you want to complete against, defaulting to +`helm-pattern' which is the value of what you enter in minibuffer. +Note that when using a function as COLLECTION this value will be +available with the input argument of the function only when using a +sync source from `helm-comp-read', i.e not using +`:candidates-in-buffer', otherwise the function is called only once +with an empty string as value for `helm-pattern' because +`helm-pattern' is not yet computed, which is what we want otherwise +data would not be fully collected at init time. + +If COLLECTION is an `obarray', a TEST should be needed. See `obarray'." + ;; Ensure COLLECTION is computed from `helm-current-buffer' + ;; because some functions used as COLLECTION work + ;; only in the context of current-buffer (Issue #1030) . + (with-helm-current-buffer + (let ((cands + (cond ((vectorp collection) + (all-completions input collection test)) + ((and (symbolp collection) (boundp collection) + ;; Issue #324 history is let-bounded and given + ;; quoted as hist argument of completing-read. + ;; See example in `rcirc-browse-url'. + (symbolp (symbol-value collection))) + nil) + ;; When collection is a symbol, most of the time + ;; it should be a symbol used as a minibuffer-history. + ;; The value of this symbol in this case return a list + ;; of string which maybe are converted later as symbol + ;; in special cases. + ;; we treat here commandp as a special case as it return t + ;; also with a string unless its last arg is provided. + ;; Also, the history collections generally collect their + ;; elements as string, so intern them to call predicate. + ((and (symbolp collection) (boundp collection) test) + (let ((predicate (lambda (elm) + (condition-case _err + (if (eq test 'commandp) + (funcall test (intern elm)) + (funcall test elm)) + (wrong-type-argument + (funcall test (intern elm))))))) + (all-completions input (symbol-value collection) predicate))) + ((and (symbolp collection) (boundp collection)) + (all-completions input (symbol-value collection))) + ;; Normally file completion should not be handled here, + ;; but special cases like `find-file-at-point' do it. + ;; Handle here specially such cases. + ((and (functionp collection) (not (string= input "")) + minibuffer-completing-file-name) + (cl-loop for f in (funcall collection input test) + unless (member f '("./" "../")) + if (string-match helm--url-regexp input) + collect f + else + collect (concat (file-name-as-directory + (helm-basedir input)) + f))) + ((functionp collection) + (funcall collection input test t)) + ((and alistp (null test)) collection) + ;; Next test ensure circular objects are removed + ;; with `all-completions' (Issue #1530). + (t (all-completions input collection test))))) + (if sort-fn (sort cands sort-fn) cands)))) + +(defun helm-cr--pattern-in-candidates-p (candidates) + (or (assoc helm-pattern candidates) + (assq (intern helm-pattern) candidates) + (member helm-pattern candidates) + (member (downcase helm-pattern) candidates) + (member (upcase helm-pattern) candidates))) + +(defun helm-cr-default-transformer (candidates source) + "Default filter candidate function for `helm-comp-read'." + (let ((must-match (helm-attr 'must-match source)) + unknown-pattern) + (unless (or (eq must-match t) + (string= helm-pattern "") + (helm-cr--pattern-in-candidates-p candidates)) + (setq candidates (append (list + ;; Unquote helm-pattern + ;; when it is added + ;; as candidate: Why? #2015 + ;; (replace-regexp-in-string + ;; "\\s\\" "" helm-pattern) + helm-pattern) + candidates)) + ;; Notify pattern have been added to candidates. + (setq unknown-pattern t)) + (cl-loop for c in candidates + for cand = (if (stringp c) + (replace-regexp-in-string "\\s\\" "" c) + c) + for pat = (replace-regexp-in-string "\\s\\" "" helm-pattern) + if (and (or (equal c pat) (equal c helm-pattern)) + unknown-pattern) + collect + (cons (concat (propertize + " " 'display + (propertize "[?]" 'face 'helm-ff-prefix)) + c) + c) + into lst + else collect (if (and (stringp cand) + (string-match "\n" cand)) + (cons (replace-regexp-in-string "\n" "->" c) c) + c) + into lst + finally return (helm-fast-remove-dups lst :test 'equal)))) + +(defun helm-comp-read--move-to-first-real-candidate () + (helm-aif (helm-get-selection nil 'withprop) + (when (string= (get-text-property 0 'display it) "[?]") + (helm-next-line)))) + +(defun helm-cr-default (default cands) + (delq nil + (cond ((and (stringp default) (not (string= default ""))) + (cons default (delete default cands))) + ((consp default) + (append (cl-loop for d in default + ;; Don't convert + ;; nil to "nil" (i.e the string) + ;; it will be delq'ed on top. + collect (if (null d) d (helm-stringify d))) + cands)) + (t cands)))) + +;;;###autoload +(cl-defun helm-comp-read (prompt collection + &key + test + initial-input + default + preselect + (buffer "*Helm Completions*") + must-match + fuzzy + reverse-history + (requires-pattern 0) + history + input-history + (case-fold helm-comp-read-case-fold-search) + (del-input t) + (persistent-action nil) + (persistent-help "DoNothing") + (mode-line helm-comp-read-mode-line) + help-message + (keymap helm-comp-read-map) + (name "Helm Completions") + header-name + candidates-in-buffer + match-part + match-dynamic + exec-when-only-one + quit-when-no-cand + (volatile t) + sort + fc-transformer + hist-fc-transformer + marked-candidates + nomark + (alistp t) + (candidate-number-limit helm-candidate-number-limit) + multiline + allow-nest + (group 'helm)) + "Read a string in the minibuffer, with helm completion. + +It is helm `completing-read' equivalent. + +- PROMPT is the prompt name to use. + +- COLLECTION can be a list, vector, obarray or hash-table. + It can be also a function that receives three arguments: + the values string, predicate and t. See `all-completions' for more details. + +Keys description: + +- TEST: A predicate called with one arg i.e candidate. + +- INITIAL-INPUT: Same as input arg in `helm'. + +- PRESELECT: See preselect arg of `helm'. + +- DEFAULT: This option is used only for compatibility with regular + Emacs `completing-read' (Same as DEFAULT arg of `completing-read'). + +- BUFFER: Name of helm-buffer. + +- MUST-MATCH: Candidate selected must be one of COLLECTION. + +- FUZZY: Enable fuzzy matching. + +- REVERSE-HISTORY: When non--nil display history source after current + source completion. + +- REQUIRES-PATTERN: Same as helm attribute, default is 0. + +- HISTORY: A list containing specific history, default is nil. + When it is non--nil, all elements of HISTORY are displayed in + a special source before COLLECTION. + +- INPUT-HISTORY: A symbol. the minibuffer input history will be + stored there, if nil or not provided, `minibuffer-history' + will be used instead. + +- CASE-FOLD: Same as `helm-case-fold-search'. + +- DEL-INPUT: Boolean, when non--nil (default) remove the partial + minibuffer input from HISTORY is present. + +- PERSISTENT-ACTION: A function called with one arg i.e candidate. + +- PERSISTENT-HELP: A string to document PERSISTENT-ACTION. + +- MODE-LINE: A string or list to display in mode line. + Default is `helm-comp-read-mode-line'. + +- KEYMAP: A keymap to use in this `helm-comp-read'. + (the keymap will be shared with history source) + +- NAME: The name related to this local source. + +- HEADER-NAME: A function to alter NAME, see `helm'. + +- EXEC-WHEN-ONLY-ONE: Bound `helm-execute-action-at-once-if-one' + to non--nil. (possibles values are t or nil). + +- VOLATILE: Use volatile attribute. + +- SORT: A predicate to give to `sort' e.g `string-lessp' + Use this only on small data as it is ineficient. + If you want to sort faster add a sort function to + FC-TRANSFORMER. + Note that FUZZY when enabled is already providing a sort function. + +- FC-TRANSFORMER: A `filtered-candidate-transformer' function + or a list of functions. + +- HIST-FC-TRANSFORMER: A `filtered-candidate-transformer' + function for the history source. + +- MARKED-CANDIDATES: If non--nil return candidate or marked candidates as a list. + +- NOMARK: When non--nil don't allow marking candidates. + +- ALISTP: (default is non--nil) See `helm-comp-read-get-candidates'. + +- CANDIDATES-IN-BUFFER: when non--nil use a source build with + `helm-source-in-buffer' which is much faster. + Argument VOLATILE have no effect when CANDIDATES-IN-BUFFER is non--nil. + +- MATCH-PART: Allow matching only one part of candidate. + See match-part documentation in `helm-source'. + +- MATCH-DYNAMIC: See match-dynamic in `helm-source-sync' + It have no effect when used with CANDIDATES-IN-BUFFER. + +- ALLOW-NEST: Allow nesting this `helm-comp-read' in a helm session. + See `helm'. + +- MULTILINE: See multiline in `helm-source'. + +- GROUP: See group in `helm-source'. + +Any prefix args passed during `helm-comp-read' invocation will be recorded +in `helm-current-prefix-arg', otherwise if prefix args were given before +`helm-comp-read' invocation, the value of `current-prefix-arg' will be used. +That's mean you can pass prefix args before or after calling a command +that use `helm-comp-read' See `helm-M-x' for example." + + (when (get-buffer helm-action-buffer) + (kill-buffer helm-action-buffer)) + (let ((action-fn `(("Sole action (Identity)" + . (lambda (candidate) + (if ,marked-candidates + (helm-marked-candidates) + (identity candidate))))))) + ;; Assume completion have been already required, + ;; so always use 'confirm. + (when (eq must-match 'confirm-after-completion) + (setq must-match 'confirm)) + (let* ((minibuffer-completion-confirm must-match) + (must-match-map (when must-match + (let ((map (make-sparse-keymap))) + (define-key map (kbd "RET") + 'helm-confirm-and-exit-minibuffer) + map))) + (loc-map (if must-match-map + (make-composed-keymap + must-match-map (or keymap helm-map)) + (or keymap helm-map))) + (minibuffer-completion-predicate test) + (minibuffer-completion-table collection) + (helm-read-file-name-mode-line-string + (replace-regexp-in-string "helm-maybe-exit-minibuffer" + "helm-confirm-and-exit-minibuffer" + helm-read-file-name-mode-line-string)) + (get-candidates + (lambda () + (let ((cands (helm-comp-read-get-candidates + ;; If `helm-pattern' is passed as INPUT + ;; and :alistp is nil INPUT is passed to + ;; `all-completions' which defeat helm + ;; matching functions (multi match, fuzzy + ;; etc...) issue #2134. + collection test sort alistp + (if (and match-dynamic (null candidates-in-buffer)) + helm-pattern "")))) + (helm-cr-default default cands)))) + (history-get-candidates + (lambda () + (let ((cands (helm-comp-read-get-candidates + history test nil alistp))) + (when cands + (delete "" (helm-cr-default default cands)))))) + (src-hist (helm-build-sync-source (format "%s History" name) + :candidates history-get-candidates + :fuzzy-match fuzzy + :multiline multiline + :match-part match-part + :filtered-candidate-transformer + (append '((lambda (candidates sources) + (cl-loop for i in candidates + ;; Input is added to history in completing-read's + ;; and may be regexp-quoted, so unquote it + ;; but check if cand is a string (it may be at this stage + ;; a symbol or nil) Issue #1553. + when (stringp i) + collect (replace-regexp-in-string "\\s\\" "" i)))) + (and hist-fc-transformer (helm-mklist hist-fc-transformer))) + :persistent-action persistent-action + :persistent-help persistent-help + :keymap loc-map + :group group + :mode-line mode-line + :help-message help-message + :action action-fn)) + (src (helm-build-sync-source name + :candidates get-candidates + :match-part match-part + :multiline multiline + :header-name header-name + :filtered-candidate-transformer + (let ((transformers (helm-mklist fc-transformer))) + (append transformers + (unless (member 'helm-cr-default-transformer transformers) + '(helm-cr-default-transformer)))) + :requires-pattern requires-pattern + :persistent-action persistent-action + :persistent-help persistent-help + :fuzzy-match fuzzy + :keymap loc-map + :group group + :mode-line mode-line + :match-dynamic match-dynamic + :help-message help-message + :action action-fn + :volatile volatile)) + (src-1 (helm-build-in-buffer-source name + :data get-candidates + :match-part match-part + :multiline multiline + :header-name header-name + :filtered-candidate-transformer + (append (helm-mklist fc-transformer) + '(helm-cr-default-transformer)) + :requires-pattern requires-pattern + :persistent-action persistent-action + :fuzzy-match fuzzy + :keymap loc-map + :group group + :persistent-help persistent-help + :mode-line mode-line + :help-message help-message + :action action-fn)) + (src-list (list src-hist + (cons (cons 'must-match must-match) + (if candidates-in-buffer + src-1 src)))) + (helm-execute-action-at-once-if-one exec-when-only-one) + (helm-quit-if-no-candidate quit-when-no-cand) + result) + (when nomark + (setq src-list (cl-loop for src in src-list + collect (cons '(nomark) src)))) + (when reverse-history (setq src-list (nreverse src-list))) + (add-hook 'helm-after-update-hook 'helm-comp-read--move-to-first-real-candidate) + (unwind-protect + (setq result (helm + :sources src-list + :input initial-input + :default default + :preselect preselect + :prompt prompt + :resume 'noresume + :keymap loc-map ;; Needed with empty collection. + :allow-nest allow-nest + :candidate-number-limit candidate-number-limit + :case-fold-search case-fold + :history (and (symbolp input-history) input-history) + :buffer buffer)) + (remove-hook 'helm-after-update-hook 'helm-comp-read--move-to-first-real-candidate)) + ;; Avoid adding an incomplete input to history. + (when (and result history del-input) + (cond ((and (symbolp history) ; History is a symbol. + (not (symbolp (symbol-value history)))) ; Fix Issue #324. + ;; Be sure history is not a symbol with a nil value. + (helm-aif (symbol-value history) (setcar it result))) + ((consp history) ; A list with a non--nil value. + (setcar history result)) + (t ; Possibly a symbol with a nil value. + (set history (list result))))) + (or result (helm-mode--keyboard-quit))))) + + +;; Generic completing-read +;; +;; Support also function as collection. +;; e.g M-x man is supported. +;; Support hash-table and vectors as collection. +;; NOTE: +;; Some crap emacs functions may not be supported +;; like ffap-alternate-file (bad use of completing-read) +;; and maybe others. +;; Provide a mode `helm-mode' which turn on +;; helm in all `completing-read' and `read-file-name' in Emacs. +;; +(defvar helm-completion-mode-string " Helm") + +(defvar helm-completion-mode-quit-message + "Helm completion disabled") + +(defvar helm-completion-mode-start-message + "Helm completion enabled") + +;;; Specialized handlers +;; +;; +(defun helm-completing-read-symbols + (prompt _collection test _require-match init + hist default _inherit-input-method name buffer) + "Specialized function for fast symbols completion in `helm-mode'." + (require 'helm-elisp) + (or + (helm + :sources (helm-build-in-buffer-source name + :init (lambda () + (helm-apropos-init (lambda (x) + (and (funcall test x) + (not (keywordp x)))) + (or (car-safe default) default))) + :filtered-candidate-transformer 'helm-apropos-default-sort-fn + :help-message #'helm-comp-read-help-message + :fuzzy-match helm-mode-fuzzy-match + :persistent-action + (lambda (candidate) + (helm-lisp-completion-persistent-action + candidate name)) + :persistent-help (helm-lisp-completion-persistent-help)) + :prompt prompt + :buffer buffer + :input init + :history hist + :resume 'noresume + :default (or default "")) + (helm-mode--keyboard-quit))) + + +;;; Generic completing read +;; +;; +(defun helm-completing-read-default-1 + (prompt collection test require-match + init hist default _inherit-input-method + name buffer &optional cands-in-buffer exec-when-only-one) + "Call `helm-comp-read' with same args as `completing-read'. +Extra optional arg CANDS-IN-BUFFER mean use `candidates-in-buffer' +method which is faster. +It should be used when candidate list don't need to rebuild dynamically." + (let ((history (or (car-safe hist) hist)) + (initial-input (helm-aif (pcase init + ((pred (stringp)) init) + ;; INIT is a cons cell. + (`(,l . ,_ll) l)) + it))) + (helm-comp-read + prompt collection + :test test + :history history + :reverse-history helm-mode-reverse-history + :input-history history + :must-match require-match + :alistp nil + :help-message #'helm-comp-read-help-message + :name name + :requires-pattern (if (and (stringp default) + (string= default "") + (or (eq require-match 'confirm) + (eq require-match + 'confirm-after-completion))) + 1 0) + :candidates-in-buffer cands-in-buffer + :exec-when-only-one exec-when-only-one + :fuzzy helm-mode-fuzzy-match + :buffer buffer + ;; If DEF is not provided, fallback to empty string + ;; to avoid `thing-at-point' to be appended on top of list + :default (or default "") + ;; Fail with special characters (e.g in gnus "nnimap+gmail:") + ;; if regexp-quote is not used. + ;; when init is added to history, it will be unquoted by + ;; helm-comp-read. + :initial-input initial-input))) + +(defun helm-completing-read-default-find-tag + (prompt collection test require-match + init hist default inherit-input-method + name buffer) + "Specialized `helm-mode' handler for `find-tag'." + ;; Some commands like find-tag may use `read-file-name' from inside + ;; the calculation of collection. in this case it clash with + ;; candidates-in-buffer that reuse precedent data (files) which is wrong. + ;; So (re)calculate collection outside of main helm-session. + (let* ((cands (helm-comp-read-get-candidates + collection test nil nil))) + (helm-completing-read-default-1 prompt cands test require-match + init hist default inherit-input-method + name buffer t))) + +(defun helm-completing-read-sync-default-handler + (prompt collection test require-match + init hist default inherit-input-method + name buffer) + "`helm-mode' handler using sync source as backend." + (helm-completing-read-default-1 prompt collection test require-match + init hist default inherit-input-method + name buffer)) + +(defun helm-completing-read-default-handler + (prompt collection test require-match + init hist default inherit-input-method + name buffer) + "Default `helm-mode' handler for all `completing-read'." + (helm-completing-read-default-1 prompt collection test require-match + init hist default inherit-input-method + name buffer + (null helm-completing-read-dynamic-complete))) + +(defun helm--generic-read-buffer (prompt &optional default require-match predicate) + "The `read-buffer-function' for `helm-mode'. +Affects `switch-to-buffer' and related." + (let ((collection (helm-buffer-list))) + (helm--completing-read-default + prompt collection predicate require-match nil nil default))) + +(cl-defun helm--completing-read-default + (prompt collection &optional + predicate require-match + initial-input hist def + inherit-input-method) + "An helm replacement of `completing-read'. +This function should be used only as a `completing-read-function'. + +Don't use it directly, use instead `helm-comp-read' in your programs. + +See documentation of `completing-read' and `all-completions' for details." + (let* ((current-command (or (helm-this-command) this-command)) + (str-command (helm-symbol-name current-command)) + (buf-name (format "*helm-mode-%s*" str-command)) + (entry (assq current-command + helm-completing-read-handlers-alist)) + (def-com (cdr-safe entry)) + (str-defcom (and def-com (helm-symbol-name def-com))) + (def-args (list prompt collection predicate require-match + initial-input hist def inherit-input-method)) + ;; Append the two extra args needed to set the buffer and source name + ;; in helm specialized functions. + (any-args (append def-args (list str-command buf-name))) + helm-completion-mode-start-message ; Be quiet + helm-completion-mode-quit-message + ;; Be sure this pesty *completion* buffer doesn't popup. + ;; Note: `minibuffer-with-setup-hook' may setup a lambda + ;; calling `minibuffer-completion-help' or other minibuffer + ;; functions we DONT WANT here, in these cases removing the hook + ;; (a symbol) have no effect. Issue #448. + ;; Because `minibuffer-completion-table' and + ;; `minibuffer-completion-predicate' are not bound + ;; anymore here, these functions should have no effect now, + ;; except in some rare cases like in `woman-file-name', + ;; so remove all incompatible functions + ;; from `minibuffer-setup-hook' (Issue #1205, #1240). + ;; otherwise helm have not the time to close its initial session. + (minibuffer-setup-hook + (cl-loop for h in minibuffer-setup-hook + unless (or (consp h) ; a lambda. + (byte-code-function-p h) + (memq h helm-mode-minibuffer-setup-hook-black-list)) + collect h)) + ;; Disable hack that could be used before `completing-read'. + ;; i.e (push ?\t unread-command-events). + unread-command-events + (default-handler + ;; Typically when COLLECTION is a function, we can assume + ;; the intention is completing dynamically according to + ;; input; If one want to use in-buffer handler for specific + ;; usage with a function as collection he can specify it in + ;; helm-completing-read-handlers-alist. + (if (functionp collection) + #'helm-completing-read-sync-default-handler + #'helm-completing-read-default-handler))) + (when (eq def-com 'ido) (setq def-com 'ido-completing-read)) + (unless (or (not entry) def-com) + ;; An entry in *read-handlers-alist exists but have + ;; a nil value, so we exit from here, disable `helm-mode' + ;; and run the command again with it original behavior. + ;; `helm-mode' will be restored on exit. + (cl-return-from helm--completing-read-default + (unwind-protect + (progn + (helm-mode -1) + (apply completing-read-function def-args)) + (helm-mode 1)))) + ;; If we use now `completing-read' we MUST turn off `helm-mode' + ;; to avoid infinite recursion and CRASH. It will be reenabled on exit. + (when (or (eq def-com 'completing-read) + ;; All specialized functions are prefixed by "helm" + (and (stringp str-defcom) + (not (string-match "^helm" str-defcom)))) + (helm-mode -1)) + (unwind-protect + (cond (;; An helm specialized function exists, run it. + (and def-com helm-mode) + (apply def-com any-args)) + (;; Try to handle `ido-completing-read' everywhere. + (and def-com (eq def-com 'ido-completing-read)) + (setcar (memq collection def-args) + (all-completions "" collection predicate)) + (apply def-com def-args)) + (;; User set explicitely `completing-read' or something similar + ;; in *read-handlers-alist, use this with exactly the same + ;; args as in `completing-read'. + ;; If we are here `helm-mode' is now disabled. + def-com + (apply def-com def-args)) + (;; Use by default a in-buffer handler unless + ;; COLLECTION is a function. + t + (funcall default-handler + prompt collection predicate require-match + initial-input hist def inherit-input-method + str-command buf-name))) + (helm-mode 1) + ;; When exiting minibuffer, `this-command' is set to + ;; `helm-exit-minibuffer', which is unwanted when starting + ;; on another `completing-read', so restore `this-command' to + ;; initial value when exiting. + (setq this-command current-command)))) + +;;; Generic read-file-name +;; +;; +;;;###autoload +(cl-defun helm-read-file-name + (prompt + &key + (name "Read File Name") + (initial-input default-directory) + (buffer "*Helm file completions*") + test + noret + (case-fold helm-file-name-case-fold-search) + preselect + history + must-match + (fuzzy t) + default + marked-candidates + (candidate-number-limit helm-ff-candidate-number-limit) + nomark + (alistp t) + (persistent-action-if 'helm-find-files-persistent-action-if) + (persistent-help "Hit1 Expand Candidate, Hit2 or (C-u) Find file") + (mode-line helm-read-file-name-mode-line-string)) + "Read a file name with helm completion. +It is helm `read-file-name' emulation. + +Argument PROMPT is the default prompt to use. + +Keys description: + +- NAME: Source name, default to \"Read File Name\". + +- INITIAL-INPUT: Where to start read file name, default to `default-directory'. + +- BUFFER: `helm-buffer' name default to \"*Helm Completions*\". + +- TEST: A predicate called with one arg 'candidate'. + +- NORET: Allow disabling helm-ff-RET (have no effect if helm-ff-RET + isn't bound to RET). + +- CASE-FOLD: Same as `helm-case-fold-search'. + +- PRESELECT: helm preselection. + +- HISTORY: Display HISTORY in a special source. + +- MUST-MATCH: Can be 'confirm, nil, or t. + +- FUZZY: Enable fuzzy matching when non-nil (Enabled by default). + +- MARKED-CANDIDATES: When non--nil return a list of marked candidates. + +- NOMARK: When non--nil don't allow marking candidates. + +- ALISTP: Don't use `all-completions' in history (take effect only on history). + +- PERSISTENT-ACTION-IF: a persistent if action function. + +- PERSISTENT-HELP: persistent help message. + +- MODE-LINE: A mode line message, default is `helm-read-file-name-mode-line-string'." + (require 'tramp) + (when (get-buffer helm-action-buffer) + (kill-buffer helm-action-buffer)) + ;; Assume completion have been already required, + ;; so always use 'confirm. + (when (eq must-match 'confirm-after-completion) + (setq must-match 'confirm)) + (mapc (lambda (hook) + (add-hook 'helm-after-update-hook hook)) + '(helm-ff-move-to-first-real-candidate + helm-ff-update-when-only-one-matched + helm-ff-auto-expand-to-home-or-root)) + (let* ((action-fn `(("Sole action (Identity)" + . (lambda (candidate) + (if ,marked-candidates + (helm-marked-candidates :with-wildcard t) + (identity candidate)))))) + ;; Be sure we don't erase the underlying minibuffer if some. + (helm-ff-auto-update-initial-value + (and helm-ff-auto-update-initial-value + (not (minibuffer-window-active-p (minibuffer-window))))) + helm-follow-mode-persistent + (helm-ff-fuzzy-matching + (and fuzzy + (not (memq helm-mm-matching-method '(multi1 multi3p))))) + (hist (and history (helm-comp-read-get-candidates + history nil nil alistp))) + (minibuffer-completion-confirm must-match) + (helm-ff--RET-disabled noret) + (must-match-map (when must-match + (let ((map (make-sparse-keymap))) + (define-key map (kbd "RET") + (let ((fn (lookup-key helm-read-file-map (kbd "RET")))) + (if (and (eq fn 'helm-ff-RET) + (null helm-ff--RET-disabled)) + #'helm-ff-RET-must-match + #'helm-confirm-and-exit-minibuffer))) + map))) + (cmap (if must-match-map + (make-composed-keymap + must-match-map helm-read-file-map) + helm-read-file-map)) + (minibuffer-completion-predicate test) + (minibuffer-completing-file-name t) + (helm--completing-file-name t) + (helm-read-file-name-mode-line-string + (replace-regexp-in-string "helm-maybe-exit-minibuffer" + "helm-confirm-and-exit-minibuffer" + helm-read-file-name-mode-line-string)) + (src-list + (list + ;; History source. + (helm-build-sync-source (format "%s History" name) + :header-name (lambda (name) + (concat name (substitute-command-keys + helm-find-files-doc-header))) + :mode-line mode-line + :candidates hist + :nohighlight t + :fuzzy-match fuzzy + :persistent-action-if persistent-action-if + :persistent-help persistent-help + :keymap cmap + :nomark nomark + :action action-fn) + ;; Other source. + (helm-build-sync-source name + :header-name (lambda (name) + (concat name (substitute-command-keys + helm-find-files-doc-header))) + :init (lambda () + (setq helm-ff-auto-update-flag + helm-ff-auto-update-initial-value) + (setq helm-ff--auto-update-state + helm-ff-auto-update-flag)) + :mode-line mode-line + :help-message 'helm-read-file-name-help-message + :nohighlight t + :candidates + (lambda () + (append (and (not (file-exists-p helm-pattern)) + (not (helm-ff--invalid-tramp-name-p helm-pattern)) + (list helm-pattern)) + (if test + (cl-loop with hn = (helm-ff--tramp-hostnames) + for i in (helm-find-files-get-candidates + must-match) + when (or (member i hn) ; A tramp host + (funcall test i)) ; Test ok + collect i) + (helm-find-files-get-candidates must-match)))) + :filtered-candidate-transformer 'helm-ff-sort-candidates + :filter-one-by-one 'helm-ff-filter-candidate-one-by-one + :persistent-action-if persistent-action-if + :persistent-help persistent-help + :volatile t + :keymap cmap + :cleanup 'helm-find-files-cleanup + :nomark nomark + :action action-fn))) + ;; Helm result. + (result (helm + :sources (if helm-mode-reverse-history + (reverse src-list) src-list) + :input (expand-file-name initial-input) + :prompt prompt + :candidate-number-limit candidate-number-limit + :resume 'noresume + :case-fold-search case-fold + :default default + :buffer buffer + :full-frame nil + :preselect preselect))) + (or + (cond ((and result (stringp result) + (string= result "") "")) + ((and result + (stringp result) + (file-equal-p result initial-input) + default) + (if (listp default) (car default) default)) + ((and result (listp result)) + (mapcar #'expand-file-name result)) + ((and result (file-directory-p result)) + (file-name-as-directory (expand-file-name result))) + (result (expand-file-name result))) + (helm-mode--keyboard-quit)))) + +(defun helm-mode--default-filename (fname dir initial) + (unless dir (setq dir default-directory)) + (unless (file-name-absolute-p dir) + (setq dir (expand-file-name dir))) + (unless (or fname (consp fname)) + (setq fname (expand-file-name + (or initial buffer-file-name dir) + dir))) + (if (and fname (consp fname)) + (setq fname (cl-loop for f in fname + collect (expand-file-name f dir))) + (if (file-name-absolute-p fname) + fname (expand-file-name fname dir)))) + +(cl-defun helm--generic-read-file-name + (prompt &optional dir default-filename mustmatch initial predicate) + "Generic helm replacement of `read-file-name'. +Don't use it directly, use instead `helm-read-file-name' in your programs." + (let* ((init (or initial dir default-directory)) + (current-command (or (helm-this-command) this-command)) + (str-command (helm-symbol-name current-command)) + (helm--file-completion-sources + (cons str-command + (remove str-command helm--file-completion-sources))) + (buf-name (format "*helm-mode-%s*" str-command)) + (entry (assq current-command + helm-completing-read-handlers-alist)) + (def-com (cdr-safe entry)) + (str-defcom (and def-com (helm-symbol-name def-com))) + ;; Don't modify the original args list for emacs generic functions. + (def-args (list prompt dir default-filename mustmatch initial predicate)) + ;; Append the two extra args needed to set the buffer and source name + ;; in helm specialized functions. + (any-args (append def-args (list str-command buf-name))) + (reading-directory (eq predicate 'file-directory-p)) + helm-completion-mode-start-message ; Be quiet + helm-completion-mode-quit-message ; Same here + fname) + ;; Build `default-filename' with `dir'+`initial' when + ;; `default-filename' is not specified. + ;; See `read-file-name' docstring for more infos. + (setq default-filename (helm-mode--default-filename + default-filename dir initial)) + ;; Some functions that normally call `completing-read' can switch + ;; brutally to `read-file-name' (e.g find-tag), in this case + ;; the helm specialized function will fail because it is build + ;; for `completing-read', so set it to 'incompatible to be sure + ;; we switch to `helm-read-file-name' and don't try to call it + ;; with wrong number of args. + (when (eq def-com 'ido) + (setq def-com 'ido-read-file-name)) + (when (and def-com (> (length (help-function-arglist def-com)) 8)) + (setq def-com 'incompatible)) + (unless (or (not entry) def-com) + (cl-return-from helm--generic-read-file-name + (unwind-protect + (progn + (helm-mode -1) + (apply read-file-name-function def-args)) + (helm-mode 1)))) + ;; If we use now `read-file-name' we MUST turn off `helm-mode' + ;; to avoid infinite recursion and CRASH. It will be reenabled on exit. + (when (or (eq def-com 'read-file-name) + (eq def-com 'ido-read-file-name) + (and (stringp str-defcom) + (not (string-match "^helm" str-defcom)))) + (helm-mode -1)) + (unwind-protect + (setq fname + (cond (;; A specialized function exists, run it + ;; with the two extra args specific to helm. + ;; Note that the helm handler should ensure + ;; :initial-input is not nil i.e. Use init + ;; which fallback to default-directory instead + ;; of INITIAL. + (and def-com helm-mode + (not (eq def-com 'ido-read-file-name)) + (not (eq def-com 'incompatible))) + (apply def-com any-args)) + (;; Def-com value is `ido-read-file-name' + ;; run it with default args. + (and def-com (eq def-com 'ido-read-file-name)) + (ido-mode 1) + (apply def-com def-args)) + (;; Def-com value is `read-file-name' + ;; run it with default args. + (eq def-com 'read-file-name) + (apply def-com def-args)) + (t ; Fall back to classic `helm-read-file-name'. + (helm-read-file-name + prompt + :name str-command + :buffer buf-name + :default default-filename + ;; Helm handlers should always have a non nil INITIAL arg. + :initial-input (expand-file-name init dir) + :alistp nil + :must-match mustmatch + :test predicate + :noret reading-directory)))) + (and ido-mode (ido-mode -1)) + (helm-mode 1) + ;; Same comment as in `helm--completing-read-default'. + (setq this-command current-command)) + (if (and + ;; Using `read-directory-name'. + reading-directory + ;; `file-name-as-directory' return "./" when FNAME is + ;; empty string. + (not (string= fname ""))) + (file-name-as-directory fname) fname))) + +;; Read file name handler with history (issue #1652) +(defun helm-read-file-name-handler-1 (prompt dir default-filename + mustmatch initial predicate + name buffer) + "A `read-file-name' handler with history. +Can be added to `helm-completing-read-handlers-alist' for functions +that need a `read-file-name' function with directory history. +The `helm-find-files' history `helm-ff-history' is used here." + (let ((helm-always-two-windows t) + (helm-split-window-default-side + (if (eq helm-split-window-default-side 'same) + 'below helm-split-window-default-side)) + helm-split-window-inside-p + helm-reuse-last-window-split-state + ;; Helm handlers should always have a non nil INITIAL arg. + (init (or initial dir default-directory))) + (helm-read-file-name + prompt + :name name + :history helm-ff-history + :buffer buffer + :default default-filename + :initial-input (expand-file-name init dir) + :alistp nil + :must-match mustmatch + :test predicate))) + + +;;; Completion in region and Helm style +;; +(defun helm-mode--advice-lisp--local-variables (old--fn &rest args) + (ignore-errors + (apply old--fn args))) + +(defvar helm-completion--sorting-done nil + "Flag that notify the FCT if sorting have been done in completion function.") +(defun helm-completion-in-region-sort-fn (candidates _source) + "Default sort function for completion-in-region." + (if helm-completion--sorting-done + candidates + (sort candidates 'helm-generic-sort-fn))) + +(defun helm-mode--completion-in-region-initial-input (str) + "Highlight prefix in helm and helm-fuzzy `helm-completion-styles'." + (if (memq helm-completion-style '(helm helm-fuzzy)) + (propertize str 'read-only t 'face 'helm-mode-prefix 'rear-nonsticky t) + str)) + +(defun helm-completion-try-completion (string table pred point) + "The try completion function for `completing-styles-alist'. +Actually do nothing." + ;; AFAIU the try completion function is here to handle single + ;; element completion, in this case it throw this element without + ;; popping up *completions* buffer. If that's the case we don't need + ;; this because helm already handle this with + ;; `helm-execute-action-at-once-if-one', so returning unconditionaly + ;; nil should be fine. + (ignore string table pred point)) + +(defun helm-completion-all-completions (string table pred point) + "The all completions function for `completing-styles-alist'." + ;; FIXME: No need to bind all these value. + (cl-multiple-value-bind (all _pattern prefix _suffix _carbounds) + (helm-completion--substring-all-completions string table pred point) + (when all (nconc all (length prefix))))) + +(defun helm-completion--all-completions-multi (string collection &optional predicate) + "Allow `all-completions' multi matching on its candidates." + (all-completions "" collection (lambda (x) + (if predicate + (and (funcall predicate x) + (helm-mm-match (helm-stringify x) string)) + (helm-mm-match (helm-stringify x) string))))) + +(defun helm-completion--substring-all-completions (string table pred point) + "Collect completions from TABLE for helm completion style." + (let* ((beforepoint (substring string 0 point)) + (afterpoint (substring string point)) + (bounds (completion-boundaries beforepoint table pred afterpoint)) + (prefix (substring beforepoint 0 (car bounds))) + (suffix (substring afterpoint (cdr bounds))) + (all (if (or (string-match-p " " string) + (string-match-p "\\`!" string)) + (helm-completion--all-completions-multi string table pred) + (all-completions string table pred)))) + (list all string prefix suffix point))) + +(defun helm-completion-in-region--initial-filter (comps afun file-comp-p) + "Add annotations at end of candidates and filter out dot files." + (if file-comp-p + ;; Filter out dot files in file completion. + (cl-loop for f in comps unless + (string-match "\\`\\.\\{1,2\\}/\\'" f) + collect f) + (if afun + ;; Add annotation at end of + ;; candidate if needed, e.g. foo, this happen when + ;; completing against a quoted symbol. + (mapcar (lambda (s) + (let ((ann (funcall afun s))) + (if ann + (cons + (concat + s + (propertize + " " 'display + (propertize + ann + 'face 'completions-annotations))) + s) + s))) + comps) + comps))) + +;; Setup completion styles for helm-mode +(defun helm-mode--setup-completion-styles () + (cl-pushnew '(helm helm-completion-try-completion + helm-completion-all-completions + "helm completion style.") + completion-styles-alist + :test 'equal)) + +(defun helm-mode--disable-completion-styles () + (setq completion-styles-alist + (delete (assq 'helm completion-styles-alist) + completion-styles-alist))) + +(defun helm-completion-in-region--fix-completion-styles () + "Add helm style to `completion-styles' and filter out invalid styles." + (if (memq helm-completion-style '(helm helm-fuzzy)) + '(basic partial-completion emacs22) + (cl-loop with all-styles = (mapcar 'car completion-styles-alist) + for style in (cons 'helm completion-styles) + when (and (memq style all-styles) + (not (memq style styles))) + collect style into styles + finally return styles))) + +(defun helm-completion--adjust-metadata (metadata) + (if (memq helm-completion-style '(helm helm-fuzzy)) + metadata + (cl-flet ((compose-helm-sort-fn + (_existing-sort-fn) + (lambda (candidates) + (let ((res candidates)) + (sort res #'helm-generic-sort-fn))))) + (let ((alist (cdr metadata))) + (helm-aif (assq 'display-sort-function alist) + (setq alist (remove it alist))) + `(metadata . ,(cons + (cons 'display-sort-function + (compose-helm-sort-fn + (alist-get 'display-sort-function alist))) + alist)))))) +(put 'helm 'completion--adjust-metadata 'helm-completion--adjust-metadata) + +(defun helm--completion-in-region (start end collection &optional predicate) + "Helm replacement of `completion--in-region'. +Can be used as value for `completion-in-region-function'." + (cl-declare (special require-match prompt)) + (if (memq major-mode helm-mode-no-completion-in-region-in-modes) + (funcall helm--old-completion-in-region-function + start end collection predicate) + (advice-add + 'lisp--local-variables + :around #'helm-mode--advice-lisp--local-variables) + (let ((old--helm-completion-style helm-completion-style)) + (helm-aif (cdr (assq major-mode helm-completion-styles-alist)) + (customize-set-variable 'helm-completion-style it)) + (unwind-protect + (let* ((enable-recursive-minibuffers t) + (completion-styles (helm-completion-in-region--fix-completion-styles)) + (input (buffer-substring start end)) + (current-command (or (helm-this-command) this-command)) + (crm (eq current-command 'crm-complete)) + (str-command (helm-symbol-name current-command)) + (buf-name (format "*helm-mode-%s*" str-command)) + (require-match (or (and (boundp 'require-match) require-match) + minibuffer-completion-confirm + ;; If prompt have not been propagated here, that's + ;; probably mean we have no prompt and we are in + ;; completion-at-point or friend, so use a non--nil + ;; value for require-match. + (not (boundp 'prompt)))) + ;; `completion-extra-properties' is let-bounded in `completion-at-point'. + ;; `afun' is a closure to call against each string in `data'. + ;; it provide the annotation info for each string. + ;; e.g "foo" => "foo " where foo is a function. + ;; See Issue #407. + (afun (plist-get completion-extra-properties :annotation-function)) + (metadata (completion-metadata + (buffer-substring start (point)) + collection predicate)) + (init-space-suffix (unless (or (memq helm-completion-style '(helm-fuzzy emacs)) + (string-suffix-p " " input) + (string= input "")) + " ")) + (file-comp-p (or (eq (completion-metadata-get metadata 'category) 'file) + (helm-mode--in-file-completion-p) + ;; Assume that when `afun' and `predicate' are null + ;; we are in filename completion. + (and (null afun) (null predicate)))) + ;; `completion-all-completions' store the base-size in the last `cdr', + ;; so data looks like this: '(a b c d . 0) and (last data) == (d . 0). + base-size + (compfn (lambda (str _predicate _action) + ;; Cache data for subsequent calls when emacs + ;; style is in use, with helm style function + ;; is called only once and cache is not + ;; needed but it doesn't harm to set hash, it + ;; will not be used. + (let* ((comps + (completion-all-completions + ;; `helm-comp-read-get-candidates' + ;; set input to `helm-pattern' + ;; so no need to pass + ;; `helm-pattern' directly here. + str + collection + predicate + (length str) + metadata)) + (last-data (last comps)) + (sort-fn (and (eq helm-completion-style 'emacs) + (completion-metadata-get + metadata 'display-sort-function))) + all) + (setq base-size + (helm-aif (cdr last-data) + (prog1 (or base-size it) + (setcdr last-data nil)) + 0)) + (setq helm-completion--sorting-done (and sort-fn t)) + (setq all (copy-sequence comps)) + ;; Fall back to string-lessp sorting when + ;; str is too small as specialized + ;; sorting may be too slow (flex). + (when (and sort-fn (<= (length str) 1)) + (setq sort-fn (lambda (all) (sort all #'string-lessp)))) + (helm-completion-in-region--initial-filter + (if sort-fn (funcall sort-fn all) all) + afun file-comp-p)))) + (data (if (memq helm-completion-style '(helm helm-fuzzy)) + (funcall compfn (buffer-substring start end) nil nil) + compfn)) + (result (if (stringp data) + data + (helm-comp-read + ;; Completion-at-point and friends have no prompt. + (or (and (boundp 'prompt) prompt) "Pattern: ") + data + :name str-command + :nomark (null crm) + :marked-candidates crm + :initial-input + (cond ((and file-comp-p + (not (string-match "/\\'" input))) + (concat (helm-mode--completion-in-region-initial-input + (helm-basename input)) + init-space-suffix)) + ((string-match "/\\'" input) nil) + ((or (null require-match) + (stringp require-match)) + (helm-mode--completion-in-region-initial-input input)) + (t (concat (helm-mode--completion-in-region-initial-input input) + init-space-suffix))) + :buffer buf-name + :fc-transformer + ;; Ensure sort fn is at the end. + (append '(helm-cr-default-transformer) + (and helm-completion-in-region-default-sort-fn + (list helm-completion-in-region-default-sort-fn))) + :match-dynamic (eq helm-completion-style 'emacs) + :fuzzy (eq helm-completion-style 'helm-fuzzy) + :exec-when-only-one t + :quit-when-no-cand + (lambda () + ;; Delay message to overwrite "Quit". + (run-with-timer + 0.01 nil + (lambda () + (message "[No matches]"))) + t) ; exit minibuffer immediately. + :must-match require-match)))) + (helm-completion-in-region--insert-result result start end base-size)) + (customize-set-variable 'helm-completion-style old--helm-completion-style) + (setq helm-completion--sorting-done nil) + (advice-remove 'lisp--local-variables + #'helm-mode--advice-lisp--local-variables))))) + +(defun helm-completion-in-region--insert-result (result start end base-size) + (cond ((stringp result) + (choose-completion-string + result (current-buffer) + (list (+ start base-size) end) + completion-list-insert-choice-function)) + ((consp result) ; crm. + (let ((beg (+ start base-size)) + (sep ",")) + ;; Try to find a default separator. + (save-excursion + (goto-char beg) + (when (looking-back crm-separator (1- (point))) + (setq sep (match-string 0)))) + (funcall completion-list-insert-choice-function + beg end (mapconcat 'identity result sep)))) + (t nil))) + +(defun helm-mode--in-file-completion-p () + (with-helm-current-buffer + (run-hook-with-args-until-success 'file-name-at-point-functions))) + +(when (boundp 'completion-in-region-function) + (defconst helm--old-completion-in-region-function completion-in-region-function)) + +(defun helm-mode--disable-ido-maybe (&optional from-hook) + (when (and (boundp 'ido-everywhere) ido-everywhere) + (remove-function read-file-name-function #'ido-read-file-name) + (remove-function read-buffer-function #'ido-read-buffer) + (setq ido-everywhere nil) + (if from-hook + (user-error "Unable to turn on Ido-everywhere while Helm-mode is enabled") + (user-error "Helm-mode enabled (Ido-everywhere is incompatible with Helm-mode, disabling it)")))) + +(defun helm-mode--ido-everywhere-hook () + ;; Called only when user calls directly ido-everywhere + ;; and helm-mode is enabled. + (when helm-mode + (helm-mode--disable-ido-maybe t))) + +;;;###autoload +(define-minor-mode helm-mode + "Toggle generic helm completion. + +All functions in Emacs that use `completing-read' +or `read-file-name' and friends will use helm interface +when this mode is turned on. + +However you can modify this behavior for functions of your choice +with `helm-completing-read-handlers-alist'. + +Also commands using `completion-in-region' will be helmized when +`helm-mode-handle-completion-in-region' is non nil, you can modify +this behavior with `helm-mode-no-completion-in-region-in-modes'. + +Called with a positive arg, turn on unconditionally, with a +negative arg turn off. +You can turn it on with `helm-mode'. + +Some crap emacs functions may not be supported, +e.g `ffap-alternate-file' and maybe others +You can add such functions to `helm-completing-read-handlers-alist' +with a nil value. + +About `ido-mode': +When you are using `helm-mode', DO NOT use `ido-mode', instead if you +want some commands use `ido', add these commands to +`helm-completing-read-handlers-alist' with `ido' as value. + +Note: This mode is incompatible with Emacs23." + :group 'helm-mode + :global t + :lighter helm-completion-mode-string + (cl-assert (boundp 'completing-read-function) nil + "`helm-mode' not available, upgrade to Emacs-24") + (if helm-mode + (if (fboundp 'add-function) + (progn + (add-function :override completing-read-function + #'helm--completing-read-default) + (add-function :override read-file-name-function + #'helm--generic-read-file-name) + (add-function :override read-buffer-function + #'helm--generic-read-buffer) + (when helm-mode-handle-completion-in-region + (add-function :override completion-in-region-function + #'helm--completion-in-region) + (helm-mode--setup-completion-styles)) + ;; If user have enabled ido-everywhere BEFORE enabling + ;; helm-mode disable it and warn user about its + ;; incompatibility with helm-mode (issue #2085). + (helm-mode--disable-ido-maybe) + ;; If ido-everywhere is not enabled yet anticipate and + ;; disable it if user attempt to enable it while helm-mode + ;; is running (issue #2085). + (add-hook 'ido-everywhere-hook #'helm-mode--ido-everywhere-hook)) + (setq completing-read-function 'helm--completing-read-default + read-file-name-function 'helm--generic-read-file-name + read-buffer-function 'helm--generic-read-buffer) + (when (and (boundp 'completion-in-region-function) + helm-mode-handle-completion-in-region) + (setq completion-in-region-function #'helm--completion-in-region) + (helm-mode--setup-completion-styles)) + (message helm-completion-mode-start-message)) + (if (fboundp 'remove-function) + (progn + (remove-function completing-read-function #'helm--completing-read-default) + (remove-function read-file-name-function #'helm--generic-read-file-name) + (remove-function read-buffer-function #'helm--generic-read-buffer) + (remove-function completion-in-region-function #'helm--completion-in-region) + (helm-mode--disable-completion-styles) + (remove-hook 'ido-everywhere-hook #'helm-mode--ido-everywhere-hook)) + (setq completing-read-function (and (fboundp 'completing-read-default) + 'completing-read-default) + read-file-name-function (and (fboundp 'read-file-name-default) + 'read-file-name-default) + read-buffer-function (and (fboundp 'read-buffer) 'read-buffer)) + (when (and (boundp 'completion-in-region-function) + (boundp 'helm--old-completion-in-region-function)) + (setq completion-in-region-function helm--old-completion-in-region-function) + (helm-mode--disable-completion-styles)) + (message helm-completion-mode-quit-message)))) + +(provide 'helm-mode) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-mode.el ends here diff --git a/elpa/helm-20191031.839/helm-net.el b/elpa/helm-20191031.839/helm-net.el new file mode 100644 index 00000000..59687009 --- /dev/null +++ b/elpa/helm-20191031.839/helm-net.el @@ -0,0 +1,431 @@ +;;; helm-net.el --- helm browse url and search web. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'cl-lib) +(require 'helm) +(require 'helm-help) +(require 'url) +(require 'xml) +(require 'browse-url) + + +(defgroup helm-net nil + "Net related applications and libraries for Helm." + :group 'helm) + +(defcustom helm-google-suggest-default-browser-function nil + "The browse url function you prefer to use with google suggest. +When nil, use the first browser function available +See `helm-browse-url-default-browser-alist'." + :group 'helm-net + :type 'symbol) + +(defcustom helm-home-url "https://www.google.com" + "Default url to use as home url." + :group 'helm-net + :type 'string) + +(defcustom helm-surfraw-default-browser-function nil + "The browse url function you prefer to use with surfraw. +When nil, fallback to `browse-url-browser-function'." + :group 'helm-net + :type 'symbol) + +(defcustom helm-google-suggest-url + "https://encrypted.google.com/complete/search?output=toolbar&q=%s" + "URL used for looking up Google suggestions. +This is a format string, don't forget the `%s'." + :type 'string + :group 'helm-net) + +(defcustom helm-google-suggest-search-url + "https://encrypted.google.com/search?ie=utf-8&oe=utf-8&q=%s" + "URL used for Google searching. +This is a format string, don't forget the `%s'." + :type 'string + :group 'helm-net) + +(defvaralias 'helm-google-suggest-use-curl-p 'helm-net-prefer-curl) +(make-obsolete-variable 'helm-google-suggest-use-curl-p 'helm-net-prefer-curl "1.7.7") + +(defcustom helm-net-prefer-curl nil + "When non--nil use CURL external program to fetch data. +Otherwise `url-retrieve-synchronously' is used." + :type 'boolean + :group 'helm-net) + +(defcustom helm-surfraw-duckduckgo-url + "https://duckduckgo.com/lite/?q=%s&kp=1" + "The duckduckgo url. +This is a format string, don't forget the `%s'. +If you have personal settings saved on duckduckgo you should have +a personal url, see your settings on duckduckgo." + :type 'string + :group 'helm-net) + +(defcustom helm-search-suggest-action-wikipedia-url + "https://en.wikipedia.org/wiki/Special:Search?search=%s" + "The Wikipedia search url. +This is a format string, don't forget the `%s'." + :type 'string + :group 'helm-net) + +(defcustom helm-search-suggest-action-youtube-url + "https://www.youtube.com/results?aq=f&search_query=%s" + "The Youtube search url. +This is a format string, don't forget the `%s'." + :type 'string + :group 'helm-net) + +(defcustom helm-search-suggest-action-imdb-url + "http://www.imdb.com/find?s=all&q=%s" + "The IMDb search url. +This is a format string, don't forget the `%s'." + :type 'string + :group 'helm-net) + +(defcustom helm-search-suggest-action-google-maps-url + "https://maps.google.com/maps?f=q&source=s_q&q=%s" + "The Google Maps search url. +This is a format string, don't forget the `%s'." + :type 'string + :group 'helm-net) + +(defcustom helm-search-suggest-action-google-news-url + "https://www.google.com/search?safe=off&prmd=nvlifd&source=lnms&tbs=nws:1&q=%s" + "The Google News search url. +This is a format string, don't forget the `%s'." + :type 'string + :group 'helm-net) + +(defcustom helm-google-suggest-actions + '(("Google Search" . helm-google-suggest-action) + ("Wikipedia" . (lambda (candidate) + (helm-search-suggest-perform-additional-action + helm-search-suggest-action-wikipedia-url + candidate))) + ("Youtube" . (lambda (candidate) + (helm-search-suggest-perform-additional-action + helm-search-suggest-action-youtube-url + candidate))) + ("IMDb" . (lambda (candidate) + (helm-search-suggest-perform-additional-action + helm-search-suggest-action-imdb-url + candidate))) + ("Google Maps" . (lambda (candidate) + (helm-search-suggest-perform-additional-action + helm-search-suggest-action-google-maps-url + candidate))) + ("Google News" . (lambda (candidate) + (helm-search-suggest-perform-additional-action + helm-search-suggest-action-google-news-url + candidate)))) + "List of actions for google suggest sources." + :group 'helm-net + :type '(alist :key-type string :value-type function)) + +(defcustom helm-browse-url-firefox-new-window "-new-tab" + "Allow choosing to browse url in new window or new tab. +Can be \"-new-tab\" (default) or \"-new-window\"." + :group 'helm-net + :type '(radio + (const :tag "New tab" "-new-tab") + (const :tag "New window" "-new-window"))) + +(defcustom helm-net-curl-switches '("-s" "-L") + "Arguments list passed to curl when using `helm-net-prefer-curl'." + :group 'helm-net + :type '(repeat string)) + +;;; Additional actions for search suggestions +;; +;; +;; Internal + +(defun helm-search-suggest-perform-additional-action (url query) + "Perform the search via URL using QUERY as input." + (browse-url (format url (url-hexify-string query)))) + +(defun helm-net--url-retrieve-sync (request parser) + (if helm-net-prefer-curl + (with-temp-buffer + (apply #'call-process "curl" + nil t nil request helm-net-curl-switches) + (funcall parser)) + (with-current-buffer (url-retrieve-synchronously request) + (funcall parser)))) + + +;;; Google Suggestions +;; +;; +(defun helm-google-suggest-parser () + (cl-loop + with result-alist = (xml-get-children + (car (xml-parse-region + (point-min) (point-max))) + 'CompleteSuggestion) + for i in result-alist collect + (cdr (cl-caadr (assq 'suggestion i))))) + +(defun helm-google-suggest-fetch (input) + "Fetch suggestions for INPUT from XML buffer." + (let ((request (format helm-google-suggest-url + (url-hexify-string input)))) + (helm-net--url-retrieve-sync + request #'helm-google-suggest-parser))) + +(defun helm-google-suggest-set-candidates (&optional request-prefix) + "Set candidates with result and number of google results found." + (let ((suggestions (helm-google-suggest-fetch + (or (and request-prefix + (concat request-prefix + " " helm-pattern)) + helm-pattern)))) + (if (member helm-pattern suggestions) + suggestions + ;; if there is no suggestion exactly matching the input then + ;; prepend a Search on Google item to the list + (append + suggestions + (list (cons (format "Search for '%s' on Google" helm-input) + helm-input)))))) + +(defun helm-ggs-set-number-result (num) + (if num + (progn + (and (numberp num) (setq num (number-to-string num))) + (cl-loop for i in (reverse (split-string num "" t)) + for count from 1 + append (list i) into C + when (= count 3) + append (list ",") into C + and do (setq count 0) + finally return + (replace-regexp-in-string + "^," "" (mapconcat 'identity (reverse C) "")))) + "?")) + +(defun helm-google-suggest-action (candidate) + "Default action to jump to a google suggested candidate." + (let ((arg (format helm-google-suggest-search-url + (url-hexify-string candidate)))) + (helm-aif helm-google-suggest-default-browser-function + (funcall it arg) + (helm-browse-url arg)))) + +(defvar helm-google-suggest-default-function + 'helm-google-suggest-set-candidates + "Default function to use in helm google suggest.") + +(defvar helm-source-google-suggest + (helm-build-sync-source "Google Suggest" + :candidates (lambda () + (funcall helm-google-suggest-default-function)) + :action 'helm-google-suggest-actions + :volatile t + :keymap helm-map + :requires-pattern 3)) + +(defun helm-google-suggest-emacs-lisp () + "Try to emacs lisp complete with google suggestions." + (helm-google-suggest-set-candidates "emacs lisp")) + + +;;; Web browser functions. +;; +;; +;; If default setting of `w3m-command' is not +;; what you want and you modify it, you will have to reeval +;; also `helm-browse-url-default-browser-alist'. + +(defvar helm-browse-url-chromium-program "chromium-browser") +(defvar helm-browse-url-uzbl-program "uzbl-browser") +(defvar helm-browse-url-conkeror-program "conkeror") +(defvar helm-browse-url-opera-program "opera") +(defvar helm-browse-url-default-browser-alist + `((,(or (and (boundp 'w3m-command) w3m-command) + "/usr/bin/w3m") . w3m-browse-url) + (,browse-url-firefox-program . browse-url-firefox) + (,helm-browse-url-chromium-program . helm-browse-url-chromium) + (,helm-browse-url-conkeror-program . helm-browse-url-conkeror) + (,helm-browse-url-opera-program . helm-browse-url-opera) + (,helm-browse-url-uzbl-program . helm-browse-url-uzbl) + (,browse-url-kde-program . browse-url-kde) + (,browse-url-gnome-moz-program . browse-url-gnome-moz) + (,browse-url-mozilla-program . browse-url-mozilla) + (,browse-url-galeon-program . browse-url-galeon) + (,browse-url-netscape-program . browse-url-netscape) + (,browse-url-mosaic-program . browse-url-mosaic) + (,browse-url-xterm-program . browse-url-text-xterm) + ("emacs" . eww-browse-url)) + "*Alist of \(executable . function\) to try to find a suitable url browser.") + +(cl-defun helm-generic-browser (url cmd-name &rest args) + "Browse URL with NAME browser." + (let ((proc (concat cmd-name " " url))) + (message "Starting %s..." cmd-name) + (apply 'start-process proc nil cmd-name + (append args (list url))) + (set-process-sentinel + (get-process proc) + (lambda (process event) + (when (string= event "finished\n") + (message "%s process %s" process event)))))) + +;;;###autoload +(defun helm-browse-url-firefox (url &optional _ignore) + "Same as `browse-url-firefox' but detach from emacs. + +So when you quit emacs you can keep your firefox session open +and not be prompted to kill firefox process. + +NOTE: Probably not supported on some systems (e.g Windows)." + (interactive (list (read-string "URL: " (browse-url-url-at-point)) + nil)) + (setq url (browse-url-encode-url url)) + (let ((process-environment (browse-url-process-environment))) + (call-process-shell-command + (format "(%s %s %s &)" + browse-url-firefox-program + helm-browse-url-firefox-new-window + (shell-quote-argument url))))) + +;;;###autoload +(defun helm-browse-url-opera (url &optional _ignore) + "Browse URL with opera browser and detach from emacs. + +So when you quit emacs you can keep your opera session open +and not be prompted to kill opera process. + +NOTE: Probably not supported on some systems (e.g Windows)." + (interactive (list (read-string "URL: " (browse-url-url-at-point)) + nil)) + (setq url (browse-url-encode-url url)) + (let ((process-environment (browse-url-process-environment))) + (call-process-shell-command + (format "(%s %s &)" + helm-browse-url-opera-program (shell-quote-argument url))))) + +;;;###autoload +(defun helm-browse-url-chromium (url &optional _ignore) + "Browse URL with google chrome browser." + (interactive "sURL: ") + (helm-generic-browser + url helm-browse-url-chromium-program)) + +;;;###autoload +(defun helm-browse-url-uzbl (url &optional _ignore) + "Browse URL with uzbl browser." + (interactive "sURL: ") + (helm-generic-browser url helm-browse-url-uzbl-program "-u")) + +;;;###autoload +(defun helm-browse-url-conkeror (url &optional _ignore) + "Browse URL with conkeror browser." + (interactive "sURL: ") + (helm-generic-browser url helm-browse-url-conkeror-program)) + +(defun helm-browse-url-default-browser (url &rest args) + "Find the first available browser and ask it to load URL." + (let ((default-browser-fn + (cl-loop for (exe . fn) in helm-browse-url-default-browser-alist + thereis (and exe (executable-find exe) (fboundp fn) fn)))) + (if default-browser-fn + (apply default-browser-fn url args) + (error "No usable browser found")))) + +(defun helm-browse-url (url &rest args) + "Default command to browse URL." + (if browse-url-browser-function + (browse-url url args) + (helm-browse-url-default-browser url args))) + + +;;; Surfraw +;; +;; Need external program surfraw. +;; + +;; Internal +(defvar helm-surfraw-engines-history nil) +(defvar helm-surfraw-input-history nil) +(defvar helm-surfraw--elvi-cache nil) + +(defun helm-build-elvi-list () + "Return list of all engines and descriptions handled by surfraw." + (or helm-surfraw--elvi-cache + (setq helm-surfraw--elvi-cache + (cdr (with-temp-buffer + (call-process "surfraw" nil t nil "-elvi") + (split-string (buffer-string) "\n")))))) + +;;;###autoload +(defun helm-surfraw (pattern engine) + "Preconfigured `helm' to search PATTERN with search ENGINE." + (interactive + (list + (let* ((default (if (use-region-p) + (buffer-substring-no-properties + (region-beginning) (region-end)) + (thing-at-point 'symbol))) + (prompt (if default + (format "SearchFor (default %s): " default) + "SearchFor: "))) + (read-string prompt nil 'helm-surfraw-input-history default)) + (helm-comp-read + "Engine: " + (helm-build-elvi-list) + :must-match t + :name "Surfraw Search Engines" + :del-input nil + :history helm-surfraw-engines-history))) + (let* ((engine-nodesc (car (split-string engine))) + (url (if (string= engine-nodesc "duckduckgo") + ;; "sr duckduckgo -p foo" is broken, workaround. + (format helm-surfraw-duckduckgo-url + (url-hexify-string pattern)) + (with-temp-buffer + (apply 'call-process "surfraw" nil t nil + (append (list engine-nodesc "-p") (split-string pattern))) + (replace-regexp-in-string + "\n" "" (buffer-string))))) + (browse-url-browser-function (or helm-surfraw-default-browser-function + browse-url-browser-function))) + (if (string= engine-nodesc "W") + (helm-browse-url helm-home-url) + (helm-browse-url url) + (setq helm-surfraw-engines-history + (cons engine (delete engine helm-surfraw-engines-history)))))) + +;;;###autoload +(defun helm-google-suggest () + "Preconfigured `helm' for google search with google suggest." + (interactive) + (helm-other-buffer 'helm-source-google-suggest "*helm google*")) + +(provide 'helm-net) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-net.el ends here diff --git a/elpa/helm-20191031.839/helm-occur.el b/elpa/helm-20191031.839/helm-occur.el new file mode 100644 index 00000000..72fc70ad --- /dev/null +++ b/elpa/helm-20191031.839/helm-occur.el @@ -0,0 +1,701 @@ +;;; helm-occur.el --- Incremental Occur for Helm. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + + +;;; Code: + +(require 'cl-lib) +(require 'helm) +(require 'helm-help) +(require 'helm-utils) + +;;; Internals +;; +(defvar helm-source-occur nil) +(defvar helm-source-moccur nil + "This is just a flag to add to `helm-sources-using-default-as-input'. +Don't set it to any value, it will have no effect.") +(defvar helm-occur--buffer-list nil) +(defvar helm-occur--buffer-tick nil) +(defvar helm-occur-history nil) +(defvar helm-occur--search-buffer-regexp "\\`\\([0-9]*\\)\\s-\\{1\\}\\(.*\\)\\'" + "The regexp matching candidates in helm-occur candidate buffer.") +(defvar helm-occur-mode--last-pattern nil) + + +(defvar helm-occur-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "C-c o") 'helm-occur-run-goto-line-ow) + (define-key map (kbd "C-c C-o") 'helm-occur-run-goto-line-of) + (define-key map (kbd "C-x C-s") 'helm-occur-run-save-buffer) + map) + "Keymap used in occur source.") + +(defgroup helm-occur nil + "Regexp related Applications and libraries for Helm." + :group 'helm) + +(defcustom helm-occur-actions + '(("Go to Line" . helm-occur-goto-line) + ("Goto line other window (C-u vertically)" . helm-occur-goto-line-ow) + ("Goto line new frame" . helm-occur-goto-line-of) + ("Save buffer" . helm-occur-save-results) + ) + "Actions for helm-occur." + :group 'helm-occur + :type '(alist :key-type string :value-type function)) + +(defcustom helm-occur-use-ioccur-style-keys nil + "Similar to `helm-grep-use-ioccur-style-keys' but for multi occur. + +Note that if you define this variable with `setq' your change will +have no effect, use customize instead." + :group 'helm-occur + :type 'boolean + :set (lambda (var val) + (set var val) + (if val + (progn + (define-key helm-occur-map (kbd "") 'helm-occur-right) + (define-key helm-occur-map (kbd "") 'helm-occur-run-default-action)) + (define-key helm-occur-map (kbd "") nil) + (define-key helm-occur-map (kbd "") nil)))) + +(defcustom helm-occur-always-search-in-current nil + "Helm multi occur always search in current buffer when non--nil." + :group 'helm-occur + :type 'boolean) + +(defcustom helm-occur-truncate-lines t + "Truncate lines in occur buffer when non nil." + :group 'helm-occur + :type 'boolean) + +(defcustom helm-occur-auto-update-on-resume nil + "Allow auto updating helm-occur buffer when outdated. +noask => Always update without asking +nil => Don't update but signal buffer needs update +never => Never update and do not signal buffer needs update +Any other non--nil value update after confirmation." + :group 'helm-regexp + :type '(radio :tag "Allow auto updating helm-occur buffer when outdated." + (const :tag "Always update without asking" noask) + (const :tag "Never update and do not signal buffer needs update" never) + (const :tag "Don't update but signal buffer needs update" nil) + (const :tag "Update after confirmation" t))) + +(defcustom helm-occur-candidate-number-limit 99999 + "Value of `helm-candidate-number-limit' for helm-occur." + :group 'helm-occur + :type 'integer) + +(defcustom helm-occur-buffer-substring-fn-for-modes + '((mu4e-headers-mode . buffer-substring)) + "Function to use to display buffer contents for major-mode. + +Can be one of `buffer-substring' or `buffer-substring-no-properties'. + +Note that when using `buffer-substring' initialization will be slower." + :group 'helm-regexp + :type '(alist :key-type (symbol :tag "Mode") + :value-type (radio (const :tag "With text properties" buffer-substring) + (const :tag "Without text properties" buffer-substring-no-properties)))) + + +(defface helm-moccur-buffer + '((t (:foreground "DarkTurquoise" :underline t))) + "Face used to highlight occur buffer names." + :group 'helm-occur) + +(defface helm-resume-need-update + '((t (:background "red"))) + "Face used to flash occur buffer when it needs update." + :group 'helm-occur) + + +;;;###autoload +(defun helm-occur () + "Preconfigured helm for searching lines matching pattern in `current-buffer'. + +When `helm-source-occur' is member of +`helm-sources-using-default-as-input' which is the default, +symbol at point is searched at startup. + +When a region is marked search only in this region by narrowing. + +To search in multiples buffers start from one of the commands listing +buffers (i.e. a helm command using `helm-source-buffers-list' like +`helm-mini') and use the multi occur buffers action. + +This is the helm implementation that collect lines matching pattern +like vanilla emacs `occur' but have nothing to do with it, the search +engine beeing completely different and also much faster." + (interactive) + (setq helm-source-occur + (car (helm-occur-build-sources (list (current-buffer)) "Helm occur"))) + (helm-set-local-variable 'helm-occur--buffer-list (list (current-buffer)) + 'helm-occur--buffer-tick + (list (buffer-chars-modified-tick (current-buffer)))) + (save-restriction + (let (def pos) + (when (use-region-p) + ;; When user mark defun with `mark-defun' with intention of + ;; using helm-occur on this region, it is relevant to use the + ;; thing-at-point located at previous position which have been + ;; pushed to `mark-ring'. + (setq def (save-excursion + (goto-char (setq pos (car mark-ring))) + (helm-aif (thing-at-point 'symbol) (regexp-quote it)))) + (narrow-to-region (region-beginning) (region-end))) + (unwind-protect + (helm :sources 'helm-source-occur + :buffer "*helm occur*" + :history 'helm-occur-history + :default (or def (helm-aif (thing-at-point 'symbol) + (regexp-quote it))) + :preselect (and (memq 'helm-source-occur + helm-sources-using-default-as-input) + (format "^%d:" (line-number-at-pos + (or pos (point))))) + :truncate-lines helm-occur-truncate-lines) + (deactivate-mark t))))) + +(defun helm-occur-transformer (candidates source) + "Returns CANDIDATES prefixed with line number." + (cl-loop with buf = (helm-attr 'buffer-name source) + for c in candidates collect + (when (string-match helm-occur--search-buffer-regexp c) + (let ((linum (match-string 1 c)) + (disp (match-string 2 c))) + (cons (format "%s:%s" + (propertize + linum 'face 'helm-grep-lineno + 'help-echo (buffer-file-name + (get-buffer buf))) + disp) + (string-to-number linum)))))) + +(defclass helm-moccur-class (helm-source-in-buffer) + ((buffer-name :initarg :buffer-name + :initform nil) + (moccur-buffers :initarg :moccur-buffers + :initform nil))) + +(defun helm-occur-build-sources (buffers &optional source-name) + "Build sources for helm-occur for each buffer in BUFFERS list." + (cl-loop for buf in buffers + collect + (helm-make-source (or source-name + (format "HO [%s]" + (buffer-name buf))) + 'helm-moccur-class + :buffer-name (buffer-name buf) + :match-part + (lambda (candidate) + ;; The regexp should match what is in candidate buffer, + ;; not what is displayed in helm-buffer e.g. "12 foo" + ;; and not "12:foo". + (when (string-match helm-occur--search-buffer-regexp + candidate) + (match-string 2 candidate))) + :search (lambda (pattern) + (when (string-match "\\`\\^\\([^ ]*\\)" pattern) + (setq pattern (concat "^[0-9]* \\{1\\}" (match-string 1 pattern)))) + (condition-case _err + (re-search-forward pattern nil t) + (invalid-regexp nil))) + :init `(lambda () + (with-current-buffer ,buf + (let* ((bsfn (or (cdr (assq + major-mode + helm-occur-buffer-substring-fn-for-modes)) + #'buffer-substring-no-properties)) + (contents (funcall bsfn (point-min) (point-max)))) + (helm-attrset 'get-line bsfn) + (with-current-buffer (helm-candidate-buffer 'local) + (insert contents) + (goto-char (point-min)) + (let ((linum 1)) + (insert (format "%s " linum)) + (while (re-search-forward "\n" nil t) + (cl-incf linum) + (insert (format "%s " linum)))))))) + :filtered-candidate-transformer 'helm-occur-transformer + :help-message 'helm-moccur-help-message + :nomark t + :migemo t + ;; Needed for resume. + :history 'helm-occur-history + :candidate-number-limit helm-occur-candidate-number-limit + :action 'helm-occur-actions + :requires-pattern 2 + :follow 1 + :group 'helm-occur + :keymap helm-occur-map + :resume 'helm-occur-resume-fn + :moccur-buffers buffers))) + +(defun helm-multi-occur-1 (buffers &optional input) + "Runs helm-occur on a list of buffers. +Each buffer's result is displayed in a separated source." + (let* ((curbuf (current-buffer)) + (bufs (if helm-occur-always-search-in-current + (cons curbuf (remove curbuf buffers)) + buffers)) + (sources (helm-occur-build-sources bufs)) + (helm--maybe-use-default-as-input + (not (null (memq 'helm-source-moccur + helm-sources-using-default-as-input))))) + (helm-set-local-variable 'helm-occur--buffer-list bufs + 'helm-occur--buffer-tick + (cl-loop for b in bufs collect + (buffer-chars-modified-tick + (get-buffer b)))) + (helm :sources sources + :buffer "*helm moccur*" + :history 'helm-occur-history + :default (helm-aif (thing-at-point 'symbol) (regexp-quote it)) + :input input + :truncate-lines helm-occur-truncate-lines))) + +;;; Actions +;; +(cl-defun helm-occur-action (lineno + &optional (method (quote buffer))) + "Jump to line number LINENO with METHOD. +arg METHOD can be one of buffer, buffer-other-window, buffer-other-frame." + (require 'helm-grep) + (let ((buf (if (eq major-mode 'helm-occur-mode) + (get-text-property (point) 'buffer-name) + (helm-attr 'buffer-name))) + (split-pat (helm-mm-split-pattern helm-input))) + (cl-case method + (buffer (switch-to-buffer buf)) + (buffer-other-window (helm-window-show-buffers (list buf) t)) + (buffer-other-frame (switch-to-buffer-other-frame buf))) + (with-current-buffer buf + (helm-goto-line lineno) + ;; Move point to the nearest matching regexp from bol. + (cl-loop for reg in split-pat + when (save-excursion + (condition-case _err + (if helm-migemo-mode + (helm-mm-migemo-forward reg (point-at-eol) t) + (re-search-forward reg (point-at-eol) t)) + (invalid-regexp nil))) + collect (match-beginning 0) into pos-ls + finally (when pos-ls (goto-char (apply #'min pos-ls))))))) + +(defun helm-occur-goto-line (candidate) + "From multi occur, switch to buffer and CANDIDATE line." + (helm-occur-action + candidate 'buffer)) + +(defun helm-occur-goto-line-ow (candidate) + "Go to CANDIDATE line in other window. +Same as `helm-occur-goto-line' but go in other window." + (helm-occur-action + candidate 'buffer-other-window)) + +(defun helm-occur-goto-line-of (candidate) + "Go to CANDIDATE line in new frame. +Same as `helm-occur-goto-line' but go in new frame." + (helm-occur-action + candidate 'buffer-other-frame)) + +(defun helm-occur-run-goto-line-ow () + "Run goto line other window action from `helm-occur'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-occur-goto-line-ow))) +(put 'helm-occur-run-goto-line-ow 'helm-only t) + +(defun helm-occur-run-goto-line-of () + "Run goto line new frame action from `helm-occur'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-occur-goto-line-of))) +(put 'helm-occur-run-goto-line-of 'helm-only t) + +(defun helm-occur-run-default-action () + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-occur-goto-line))) +(put 'helm-occur-run-default-action 'helm-only t) + +(defun helm-occur-run-save-buffer () + "Run moccur save results action from `helm-moccur'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-occur-save-results))) +(put 'helm-moccur-run-save-buffer 'helm-only t) + +(defun helm-occur-right () + "helm-occur action for right arrow. +This is used when `helm-occur-use-ioccur-style-keys' is enabled. +If follow is enabled (default) go to next source, otherwise execute +persistent action." + (interactive) + (if (helm-aand (helm-attr 'follow) (> it 0)) + (helm-next-source) + (helm-execute-persistent-action))) +(put 'helm-occur-right 'helm-only t) + + +;;; helm-occur-mode +;; +;; +(defvar helm-occur-mode-map + (let ((map (make-sparse-keymap))) + (define-key map (kbd "RET") 'helm-occur-mode-goto-line) + (define-key map (kbd "C-o") 'helm-occur-mode-goto-line-ow) + (define-key map (kbd "") 'helm-occur-mode-goto-line-ow-forward) + (define-key map (kbd "") 'helm-occur-mode-goto-line-ow-backward) + (define-key map (kbd "") 'helm-gm-next-file) + (define-key map (kbd "") 'helm-gm-precedent-file) + (define-key map (kbd "M-n") 'helm-occur-mode-goto-line-ow-forward) + (define-key map (kbd "M-p") 'helm-occur-mode-goto-line-ow-backward) + (define-key map (kbd "M-N") 'helm-gm-next-file) + (define-key map (kbd "M-P") 'helm-gm-precedent-file) + (define-key map (kbd "C-c b") 'helm-occur-mode-resume-session) + map)) + +(defun helm-occur-mode-goto-line () + (interactive) + (helm-aif (get-text-property (point) 'helm-realvalue) + (progn (helm-occur-goto-line it) (helm-match-line-cleanup-pulse)))) + +(defun helm-occur-mode-goto-line-ow () + (interactive) + (helm-aif (get-text-property (point) 'helm-realvalue) + (progn (helm-occur-goto-line-ow it) (helm-match-line-cleanup-pulse)))) + +(defun helm-occur-mode-goto-line-ow-forward-1 (arg) + (condition-case nil + (progn + (when (or (eq last-command 'helm-occur-mode-goto-line-ow-forward) + (eq last-command 'helm-occur-mode-goto-line-ow-backward)) + (forward-line arg)) + (save-selected-window + (helm-occur-mode-goto-line-ow) + (recenter))) + (error nil))) + +(defun helm-occur-mode-goto-line-ow-forward (arg) + (interactive "p") + (helm-occur-mode-goto-line-ow-forward-1 arg)) + +(defun helm-occur-mode-goto-line-ow-backward (arg) + (interactive "p") + (helm-occur-mode-goto-line-ow-forward-1 (- arg))) + +(defun helm-occur-save-results (_candidate) + "Save helm moccur results in a `helm-moccur-mode' buffer." + (let ((buf "*hmoccur*") + new-buf) + (when (get-buffer buf) + (setq new-buf (helm-read-string "OccurBufferName: " buf)) + (cl-loop for b in (helm-buffer-list) + when (and (string= new-buf b) + (not (y-or-n-p + (format "Buffer `%s' already exists overwrite? " + new-buf)))) + do (setq new-buf (helm-read-string + "OccurBufferName: " "*hmoccur "))) + (setq buf new-buf)) + (with-current-buffer (get-buffer-create buf) + (kill-all-local-variables) + (setq buffer-read-only t) + (buffer-disable-undo) + (let ((inhibit-read-only t) + (map (make-sparse-keymap)) + buf-name) + (erase-buffer) + (insert "-*- mode: helm-occur -*-\n\n" + (format "Occur Results for `%s':\n\n" helm-input)) + (save-excursion + (insert (with-current-buffer helm-buffer + (goto-char (point-min)) + (forward-line 1) + (buffer-substring (point) (point-max))))) + (save-excursion + (forward-line -2) + (while (not (eobp)) + (if (helm-pos-header-line-p) + (let ((beg (point-at-bol)) + (end (point-at-eol))) + (set-text-properties beg (1+ end) nil) + (delete-region (1- beg) end)) + (helm-aif (setq buf-name (assoc-default + 'buffer-name + (get-text-property (point) 'helm-cur-source))) + (progn + (insert (propertize (concat it ":") + 'face 'helm-moccur-buffer + 'helm-realvalue (get-text-property (point) 'helm-realvalue))) + (add-text-properties + (point-at-bol) (point-at-eol) + `(buffer-name ,buf-name)) + (add-text-properties + (point-at-bol) (point-at-eol) + `(keymap ,map + help-echo ,(concat + (buffer-file-name + (get-buffer buf-name)) + "\nmouse-1: set point\nmouse-2: jump to selection") + mouse-face highlight + invisible nil)) + (define-key map [mouse-1] 'mouse-set-point) + (define-key map [mouse-2] 'helm-occur-mode-mouse-goto-line) + (define-key map [mouse-3] 'ignore)))) + (forward-line 1)))) + (buffer-enable-undo) + (helm-occur-mode)) + (pop-to-buffer buf) + (message "Helm occur Results saved in `%s' buffer" buf))) + +(defun helm-occur-mode-mouse-goto-line (event) + (interactive "e") + (let* ((window (posn-window (event-end event))) + (pos (posn-point (event-end event)))) + (with-selected-window window + (when (eq major-mode 'helm-occur-mode) + (goto-char pos) + (helm-occur-mode-goto-line))))) +(put 'helm-moccur-mode-mouse-goto-line 'helm-only t) + +(defun helm-occur-mode-resume-session () + (interactive) + (cl-assert (eq major-mode 'helm-occur-mode) nil "Helm command called in wrong context") + (helm-multi-occur-1 helm-occur--buffer-list helm-occur-mode--last-pattern)) + +(defun helm-occur-buffer-substring-with-linums () + "Returns current-buffer contents as a string with all lines +numbered. The property 'buffer-name is added to the whole string." + (let ((bufstr (buffer-substring-no-properties (point-min) (point-max))) + (bufname (buffer-name))) + (with-temp-buffer + (save-excursion + (insert bufstr)) + (let ((linum 1)) + (insert (format "%s " linum)) + (while (re-search-forward "\n" nil t) + (cl-incf linum) + (insert (format "%s " linum))) + (add-text-properties (point-min) (point-max) `(buffer-name ,bufname))) + (buffer-string)))) + +(defun helm-occur-mode--revert-buffer-function (&optional _ignore-auto _noconfirm) + "The `revert-buffer-function' for `helm-occur-mode'." + (goto-char (point-min)) + (let (pattern) + (when (re-search-forward "^Occur Results for `\\(.*\\)'" nil t) + (setq pattern (match-string 1)) + (forward-line 0) + (when (re-search-forward "^$" nil t) + (forward-line 1)) + (let ((inhibit-read-only t) + (buffer (current-buffer)) + (buflst helm-occur--buffer-list)) + (delete-region (point) (point-max)) + (message "Reverting buffer...") + (save-excursion + (with-temp-buffer + (insert + "\n" + (cl-loop for buf in buflst + for bufstr = (or (and (buffer-live-p (get-buffer buf)) + (with-current-buffer buf + (helm-occur-buffer-substring-with-linums))) + "") + concat bufstr) + "\n") + (goto-char (point-min)) + (cl-loop with linum + with mpart + ;; Bind helm-pattern used by `helm-grep-split-line'. + with helm-pattern = pattern + while (helm-mm-search pattern) ; point is at eol. + ;; Calculate line number (linum) and extract real + ;; part of line (mpart). + do (when (save-excursion + ;; `helm-mm-search' puts point at eol. + (forward-line 0) + (re-search-forward "^\\([0-9]*\\)\\s-\\{1\\}\\(.*\\)$" + (point-at-eol) t)) + (setq linum (string-to-number (match-string 1)) + mpart (match-string 2))) + ;; Match part after line number. + when (and mpart (string-match pattern mpart)) + for line = (format "%s:%d:%s" + (get-text-property (point) 'buffer-name) + linum + mpart) + when line + do (with-current-buffer buffer + (insert + (propertize + (car (helm-occur-filter-one-by-one line)) + 'helm-realvalue linum) + "\n")))) + (when (fboundp 'wgrep-cleanup-overlays) + (wgrep-cleanup-overlays (point-min) (point-max))) + (message "Reverting buffer done")))))) + +(defun helm-occur-filter-one-by-one (candidate) + "`filter-one-by-one' function for `helm-source-moccur'." + (require 'helm-grep) + (let* ((split (helm-grep-split-line candidate)) + (buf (car split)) + (lineno (nth 1 split)) + (str (nth 2 split))) + (cons (concat (propertize + buf + 'face 'helm-moccur-buffer + 'help-echo (buffer-file-name + (get-buffer buf)) + 'buffer-name buf) + ":" + (propertize lineno 'face 'helm-grep-lineno) + ":" + (helm-grep-highlight-match str t)) + candidate))) + +;;;###autoload +(define-derived-mode helm-occur-mode + special-mode "helm-moccur" + "Major mode to provide actions in helm moccur saved buffer. + +Special commands: +\\{helm-occur-mode-map}" + (set (make-local-variable 'helm-occur--buffer-list) + (with-helm-buffer helm-occur--buffer-list)) + (set (make-local-variable 'revert-buffer-function) + #'helm-occur-mode--revert-buffer-function) + (set (make-local-variable 'helm-occur-mode--last-pattern) + helm-input)) +(put 'helm-moccur-mode 'helm-only t) + + +;;; Resume +;; +(defun helm-occur-resume-fn () + (with-helm-buffer + (let (new-tick-ls buffer-is-modified) + (set (make-local-variable 'helm-occur--buffer-list) + (cl-loop for b in helm-occur--buffer-list + when (buffer-live-p (get-buffer b)) + collect b)) + (setq buffer-is-modified (/= (length helm-occur--buffer-list) + (length (helm-attr 'moccur-buffers)))) + (helm-attrset 'moccur-buffers helm-occur--buffer-list) + (setq new-tick-ls (cl-loop for b in helm-occur--buffer-list + collect (buffer-chars-modified-tick + (get-buffer b)))) + (when buffer-is-modified + (setq helm-occur--buffer-tick new-tick-ls)) + (cl-assert (> (length helm-occur--buffer-list) 0) nil + "helm-resume error: helm-(m)occur buffer list is empty") + (unless (eq helm-occur-auto-update-on-resume 'never) + (when (or buffer-is-modified + (cl-loop for b in helm-occur--buffer-list + for new-tick = (buffer-chars-modified-tick + (get-buffer b)) + for tick in helm-occur--buffer-tick + thereis (/= tick new-tick))) + (helm-aif helm-occur-auto-update-on-resume + (when (or (eq it 'noask) + (y-or-n-p "Helm (m)occur Buffer outdated, update? ")) + (run-with-idle-timer + 0.1 nil (lambda () + (with-helm-buffer + (helm-force-update) + (message "Helm (m)occur Buffer have been udated") + (sit-for 1) (message nil)))) + (unless buffer-is-modified (setq helm-occur--buffer-tick + new-tick-ls))) + (run-with-idle-timer + 0.1 nil + (lambda () + (with-helm-buffer + (let ((ov (make-overlay (save-excursion + (goto-char (point-min)) + (forward-line 1) + (point)) + (point-max)))) + (overlay-put ov 'face 'helm-resume-need-update) + (sit-for 0.3) (delete-overlay ov) + (message "[Helm occur Buffer outdated (C-c C-u to update)]"))))) + (unless buffer-is-modified + (with-helm-after-update-hook + (setq helm-occur--buffer-tick new-tick-ls) + (message "Helm (m)occur Buffer have been udated"))))))))) + +;;; Helm occur from isearch +;; +;;;###autoload +(defun helm-occur-from-isearch () + "Invoke `helm-occur' from isearch. + +To use this bind it to a key in `isearch-mode-map'." + (interactive) + (let ((input (if isearch-regexp + isearch-string + (regexp-quote isearch-string))) + (bufs (list (current-buffer)))) + (isearch-exit) + (helm-multi-occur-1 bufs input))) + +;;;###autoload +(defun helm-multi-occur-from-isearch () + "Invoke `helm-multi-occur' from isearch. + +With a prefix arg, reverse the behavior of +`helm-moccur-always-search-in-current'. +The prefix arg can be set before calling +`helm-multi-occur-from-isearch' or during the buffer selection. + +To use this bind it to a key in `isearch-mode-map'." + (interactive) + (let (buf-list + helm-moccur-always-search-in-current + (input (if isearch-regexp + isearch-string + (regexp-quote isearch-string)))) + (isearch-exit) + (setq buf-list (mapcar 'get-buffer + (helm-comp-read "Buffers: " + (helm-buffer-list) + :name "Occur in buffer(s)" + :marked-candidates t))) + (setq helm-moccur-always-search-in-current + (if (or current-prefix-arg + helm-current-prefix-arg) + (not helm-moccur-always-search-in-current) + helm-moccur-always-search-in-current)) + (helm-multi-occur-1 buf-list input))) + +(provide 'helm-occur) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-occur.el ends here diff --git a/elpa/helm-20191031.839/helm-pkg.el b/elpa/helm-20191031.839/helm-pkg.el new file mode 100644 index 00000000..e6105a64 --- /dev/null +++ b/elpa/helm-20191031.839/helm-pkg.el @@ -0,0 +1,9 @@ +(define-package "helm" "20191031.839" "Helm is an Emacs incremental and narrowing framework" + '((emacs "24.4") + (async "1.9.3") + (popup "0.5.3") + (helm-core "3.0")) + :url "https://emacs-helm.github.io/helm/") +;; Local Variables: +;; no-byte-compile: t +;; End: diff --git a/elpa/helm-20191031.839/helm-regexp.el b/elpa/helm-20191031.839/helm-regexp.el new file mode 100644 index 00000000..8c2e2b3e --- /dev/null +++ b/elpa/helm-20191031.839/helm-regexp.el @@ -0,0 +1,138 @@ +;;; helm-regexp.el --- In buffer regexp searching and replacement for helm. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'cl-lib) +(require 'helm) +(require 'helm-help) +(require 'helm-utils) + +(declare-function helm-mm-split-pattern "helm-multi-match") + + +(defgroup helm-regexp nil + "Regexp related Applications and libraries for Helm." + :group 'helm) + + + +;; History vars +(defvar helm-build-regexp-history nil) + +(defun helm-query-replace-regexp (_candidate) + "Query replace regexp from `helm-regexp'. +With a prefix arg replace only matches surrounded by word boundaries, +i.e Don't replace inside a word, regexp is surrounded with \\bregexp\\b." + (let ((regexp helm-input)) + (apply 'query-replace-regexp + (helm-query-replace-args regexp)))) + +(defun helm-kill-regexp-as-sexp (_candidate) + "Kill regexp in a format usable in lisp code." + (helm-regexp-kill-new + (prin1-to-string helm-input))) + +(defun helm-kill-regexp (_candidate) + "Kill regexp as it is in `helm-pattern'." + (helm-regexp-kill-new helm-input)) + +(defun helm-query-replace-args (regexp) + "create arguments of `query-replace-regexp' action in `helm-regexp'." + (let ((region-only (helm-region-active-p))) + (list + regexp + (query-replace-read-to regexp + (format "Query replace %sregexp %s" + (if helm-current-prefix-arg "word " "") + (if region-only "in region " "")) + t) + helm-current-prefix-arg + (when region-only (region-beginning)) + (when region-only (region-end))))) + +(defvar helm-source-regexp + (helm-build-in-buffer-source "Regexp Builder" + :init (lambda () + (helm-init-candidates-in-buffer + 'global (with-temp-buffer + (insert-buffer-substring helm-current-buffer) + (buffer-string)))) + :get-line #'helm-regexp-get-line + :persistent-action #'helm-regexp-persistent-action + :persistent-help "Show this line" + :multiline t + :multimatch nil + :requires-pattern 2 + :group 'helm-regexp + :mode-line "Press TAB to select action." + :action '(("Kill Regexp as sexp" . helm-kill-regexp-as-sexp) + ("Query Replace Regexp (C-u Not inside word.)" + . helm-query-replace-regexp) + ("Kill Regexp" . helm-kill-regexp)))) + +(defun helm-regexp-get-line (s e) + (let ((matches (match-data)) + (line (buffer-substring s e))) + (propertize + (cl-loop with ln = (format "%5d: %s" (1- (line-number-at-pos s)) line) + for i from 0 to (1- (/ (length matches) 2)) + if (match-string i) + concat (format "\n%s%s'%s'" + (make-string 10 ? ) (format "Group %d: " i) it) + into ln1 + finally return (concat ln ln1)) + 'helm-realvalue s))) + +(defun helm-regexp-persistent-action (pt) + (helm-goto-char pt) + (helm-highlight-current-line)) + +(defun helm-regexp-kill-new (input) + (kill-new (substring-no-properties input)) + (message "Killed: %s" input)) + + +;;; Predefined commands +;; +;; + +;;;###autoload +(defun helm-regexp () + "Preconfigured helm to build regexps. +`query-replace-regexp' can be run from there against found regexp." + (interactive) + (save-restriction + (when (and (helm-region-active-p) + ;; Don't narrow to region if buffer is already narrowed. + (not (helm-current-buffer-narrowed-p (current-buffer)))) + (narrow-to-region (region-beginning) (region-end))) + (helm :sources helm-source-regexp + :buffer "*helm regexp*" + :prompt "Regexp: " + :history 'helm-build-regexp-history))) + + +(provide 'helm-regexp) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-regexp.el ends here diff --git a/elpa/helm-20191031.839/helm-ring.el b/elpa/helm-20191031.839/helm-ring.el new file mode 100644 index 00000000..f4504d53 --- /dev/null +++ b/elpa/helm-20191031.839/helm-ring.el @@ -0,0 +1,591 @@ +;;; helm-ring.el --- kill-ring, mark-ring, and register browsers for helm. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'cl-lib) +(require 'helm) +(require 'helm-utils) +(require 'helm-help) +(require 'helm-elisp) + +(declare-function undo-tree-restore-state-from-register "ext:undo-tree.el" (register)) + + +(defgroup helm-ring nil + "Ring related Applications and libraries for Helm." + :group 'helm) + +(defcustom helm-kill-ring-threshold 3 + "Minimum length of a candidate to be listed by `helm-source-kill-ring'." + :type 'integer + :group 'helm-ring) + +(defcustom helm-kill-ring-max-offset 400 + "Max number of chars displayed per candidate in kill-ring browser. +When `t', don't truncate candidate, show all. +By default it is approximatively the number of bits contained in five lines +of 80 chars each i.e 80*5. +Note that if you set this to nil multiline will be disabled, i.e you +will not have anymore separators between candidates." + :type '(choice (const :tag "Disabled" t) + (integer :tag "Max candidate offset")) + :group 'helm-ring) + +(defcustom helm-kill-ring-actions + '(("Yank marked" . helm-kill-ring-action-yank) + ("Delete marked" . helm-kill-ring-action-delete)) + "List of actions for kill ring source." + :group 'helm-ring + :type '(alist :key-type string :value-type function)) + +(defcustom helm-kill-ring-separator "\n" + "The separator used to separate marked candidates when yanking." + :group 'helm-ring + :type 'string) + +(defcustom helm-register-max-offset 160 + "Max size of string register entries before truncating." + :group 'helm-ring + :type 'integer) + +;;; Kill ring +;; +;; +(defvar helm-kill-ring-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "M-y") 'helm-next-line) + (define-key map (kbd "M-u") 'helm-previous-line) + (define-key map (kbd "M-D") 'helm-kill-ring-delete) + (define-key map (kbd "C-]") 'helm-kill-ring-toggle-truncated) + (define-key map (kbd "C-c C-k") 'helm-kill-ring-kill-selection) + (define-key map (kbd "C-c d") 'helm-kill-ring-run-persistent-delete) + map) + "Keymap for `helm-show-kill-ring'.") + +(defvar helm-source-kill-ring + (helm-build-sync-source "Kill Ring" + :init (lambda () + (helm-attrset 'last-command last-command) + (helm-attrset 'multiline helm-kill-ring-max-offset)) + :candidates #'helm-kill-ring-candidates + :filtered-candidate-transformer #'helm-kill-ring-transformer + :action 'helm-kill-ring-actions + :persistent-action 'ignore + :help-message 'helm-kill-ring-help-message + :persistent-help "DoNothing" + :keymap helm-kill-ring-map + :migemo t + :multiline 'helm-kill-ring-max-offset + :group 'helm-ring) + "Source for browse and insert contents of kill-ring.") + +(defun helm-kill-ring-candidates () + (cl-loop with cands = (helm-fast-remove-dups kill-ring :test 'equal) + for kill in (if (eq (helm-attr 'last-command) 'yank) + (cdr cands) + cands) + unless (or (< (length kill) helm-kill-ring-threshold) + (string-match "\\`[\n[:blank:]]+\\'" kill)) + collect kill)) + +(defun helm-kill-ring-transformer (candidates _source) + "Ensure CANDIDATES are not read-only." + (cl-loop for i in candidates + when (get-text-property 0 'read-only i) + do (set-text-properties 0 (length i) '(read-only nil) i) + collect i)) + +(defvar helm-kill-ring--truncated-flag nil) +(defun helm-kill-ring-toggle-truncated () + "Toggle truncated view of candidates in helm kill-ring browser." + (interactive) + (with-helm-alive-p + (setq helm-kill-ring--truncated-flag (not helm-kill-ring--truncated-flag)) + (let* ((cur-cand (helm-get-selection)) + (presel-fn (lambda () + (helm-kill-ring--preselect-fn cur-cand)))) + (helm-attrset 'multiline + (if helm-kill-ring--truncated-flag + 15000000 + helm-kill-ring-max-offset)) + (helm-update presel-fn)))) +(put 'helm-kill-ring-toggle-truncated 'helm-only t) + +(defun helm-kill-ring-kill-selection () + "Store the real value of candidate in kill-ring. +Same as `helm-kill-selection-and-quit' called with a prefix arg." + (interactive) + (helm-kill-selection-and-quit t)) +(put 'helm-kill-ring-kill-selection 'helm-only t) + +(defun helm-kill-ring--preselect-fn (candidate) + "Internal, used to preselect CANDIDATE when toggling truncated view." + ;; Preselection by regexp may not work if candidate is huge, so walk + ;; the helm buffer until selection is on CANDIDATE. + (helm-awhile (condition-case-unless-debug nil + (and (not (helm-pos-header-line-p)) + (helm-get-selection)) + (error nil)) + (if (string= it candidate) + (cl-return) + (helm-next-line)))) + +(defun helm-kill-ring-action-yank (_str) + "Insert concatenated marked candidates in current-buffer. + +When two prefix args are given prompt to choose separator, otherwise +use `helm-kill-ring-separator' as default." + (let ((marked (helm-marked-candidates)) + (sep (if (equal helm-current-prefix-arg '(16)) + (read-string "Separator: ") + helm-kill-ring-separator))) + (helm-kill-ring-action-yank-1 + (cl-loop for c in (butlast marked) + concat (concat c sep) into str + finally return (concat str (car (last marked))))))) + +(defun helm-kill-ring-action-yank-1 (str) + "Insert STR in `kill-ring' and set STR to the head. + +When called with a prefix arg, point and mark are exchanged without +activating region. +If this action is executed just after `yank', +replace with STR as yanked string." + (let ((yank-fn (lambda (&optional before yank-pop) + (insert-for-yank str) + ;; Set the window start back where it was in + ;; the yank command, if possible. + (when yank-pop + (set-window-start (selected-window) yank-window-start t)) + (when (or (equal helm-current-prefix-arg '(4)) before) + ;; Same as exchange-point-and-mark but without + ;; activating region. + (goto-char (prog1 (mark t) + (set-marker (mark-marker) + (point) + helm-current-buffer))))))) + ;; Prevent inserting and saving highlighted items. + (set-text-properties 0 (length str) nil str) + (with-helm-current-buffer + (unwind-protect + (progn + (setq kill-ring (delete str kill-ring)) + ;; Adding a `delete-selection' property + ;; to `helm-kill-ring-action' is not working + ;; because `this-command' will be `helm-maybe-exit-minibuffer', + ;; so use this workaround (Issue #1520). + (when (and (region-active-p) delete-selection-mode) + (delete-region (region-beginning) (region-end))) + (if (not (eq (helm-attr 'last-command helm-source-kill-ring) 'yank)) + (progn + ;; Ensure mark is at beginning of inserted text. + (push-mark) + ;; When yanking in a helm minibuffer we need a small + ;; delay to detect the mark in previous minibuffer. [1] + (run-with-timer 0.01 nil yank-fn)) + ;; from `yank-pop' + (let ((inhibit-read-only t) + (before (< (point) (mark t)))) + (if before + (funcall (or yank-undo-function 'delete-region) (point) (mark t)) + (funcall (or yank-undo-function 'delete-region) (mark t) (point))) + (setq yank-undo-function nil) + (set-marker (mark-marker) (point) helm-current-buffer) + ;; Same as [1] but use the same mark and point as in + ;; the initial yank according to BEFORE even if no + ;; prefix arg is given. + (run-with-timer 0.01 nil yank-fn before 'pop)))) + (kill-new str))))) +(define-obsolete-function-alias 'helm-kill-ring-action 'helm-kill-ring-action-yank "2.4.0") + +(defun helm-kill-ring-action-delete (_candidate) + "Delete marked candidates from `kill-ring'." + (cl-loop for c in (helm-marked-candidates) + do (setq kill-ring + (delete c kill-ring)))) + +(defun helm-kill-ring-persistent-delete (_candidate) + (unwind-protect + (cl-loop for c in (helm-marked-candidates) + do (progn + (helm-preselect (format "^%s" (regexp-quote c))) + (setq kill-ring (delete c kill-ring)) + (helm-delete-current-selection) + (helm--remove-marked-and-update-mode-line c))) + (with-helm-buffer + (setq helm-marked-candidates nil + helm-visible-mark-overlays nil)) + (helm-force-update (helm-aif (helm-get-selection nil t) (regexp-quote it))))) + +(defun helm-kill-ring-run-persistent-delete () + "Delete current candidate without quitting." + (interactive) + (with-helm-alive-p + (helm-attrset 'quick-delete '(helm-kill-ring-persistent-delete . never-split)) + (helm-execute-persistent-action 'quick-delete))) +(put 'helm-kill-ring-run-persistent-delete 'helm-only t) + +(defun helm-kill-ring-delete () + "Delete marked candidates from `kill-ring'. + +This is a command for `helm-kill-ring-map'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action 'helm-kill-ring-action-delete))) +(put 'helm-kill-ring-delete 'helm-only t) + + +;;;; +;; DO NOT use these sources with other sources use +;; the commands `helm-mark-ring', `helm-global-mark-ring' or +;; `helm-all-mark-rings' instead. + +(defun helm-mark-ring-line-string-at-pos (pos) + "Return line string at position POS." + (save-excursion + (goto-char pos) + (forward-line 0) + (let ((line (car (split-string (thing-at-point 'line) "[\n\r]")))) + (remove-text-properties 0 (length line) '(read-only) line) + (if (string= "" line) + "" + line)))) + +(defun helm-mark-ring-get-candidates () + (with-helm-current-buffer + (cl-loop with marks = (if (mark t) + (cons (mark-marker) mark-ring) + mark-ring) + for marker in marks + with max-line-number = (line-number-at-pos (point-max)) + with width = (length (number-to-string max-line-number)) + for m = (format (concat "%" (number-to-string width) "d: %s") + (line-number-at-pos marker) + (helm-mark-ring-line-string-at-pos marker)) + unless (and recip (assoc m recip)) + collect (cons m marker) into recip + finally return recip))) + +(defun helm-mark-ring-default-action (candidate) + (let ((target (copy-marker candidate))) + (helm-aif (marker-buffer candidate) + (progn + (switch-to-buffer it) + (helm-log-run-hook 'helm-goto-line-before-hook) + (helm-match-line-cleanup) + (with-helm-current-buffer + (unless helm-yank-point (setq helm-yank-point (point)))) + (helm-goto-char target) + (helm-highlight-current-line)) + ;; marker points to no buffer, no need to dereference it, just + ;; delete it. + (setq mark-ring (delete target mark-ring)) + (error "Marker points to no buffer")))) + +(defvar helm-source-mark-ring + (helm-build-sync-source "mark-ring" + :candidates #'helm-mark-ring-get-candidates + :action '(("Goto line" . helm-mark-ring-default-action)) + :persistent-help "Show this line" + :group 'helm-ring)) + +;;; Global-mark-ring +(defvar helm-source-global-mark-ring + (helm-build-sync-source "global-mark-ring" + :candidates #'helm-global-mark-ring-get-candidates + :action '(("Goto line" . helm-mark-ring-default-action)) + :persistent-help "Show this line" + :group 'helm-ring)) + +(defun helm-global-mark-ring-format-buffer (marker) + (with-current-buffer (marker-buffer marker) + (goto-char marker) + (forward-line 0) + (let ((line (pcase (thing-at-point 'line) + ((and line (pred stringp) + (guard (not (string-match-p "\\`\n?\\'" line)))) + (car (split-string line "[\n\r]"))) + (_ "")))) + (remove-text-properties 0 (length line) '(read-only) line) + (format "%7d:%s: %s" + (line-number-at-pos) (marker-buffer marker) line)))) + +(defun helm-global-mark-ring-get-candidates () + (let ((marks global-mark-ring)) + (when marks + (cl-loop for marker in marks + for mb = (marker-buffer marker) + for gm = (unless (or (string-match "^ " (format "%s" mb)) + (null mb)) + (helm-global-mark-ring-format-buffer marker)) + when (and gm (not (assoc gm recip))) + collect (cons gm marker) into recip + finally return recip)))) + +;;;; +;;; Insert from register +(defvar helm-source-register + (helm-build-sync-source "Registers" + :candidates #'helm-register-candidates + :action-transformer #'helm-register-action-transformer + :persistent-help "" + :multiline t + :action '(("Delete Register(s)" . + (lambda (_candidate) + (cl-loop for candidate in (helm-marked-candidates) + for register = (car candidate) + do (setq register-alist + (delq (assoc register register-alist) + register-alist)))))) + :group 'helm-ring) + "See (info \"(emacs)Registers\")") + +(defun helm-register-candidates () + "Collecting register contents and appropriate commands." + (cl-loop for (char . val) in register-alist + for key = (single-key-description char) + for string-actions = + (cond + ((numberp val) + (list (int-to-string val) + 'insert-register + 'increment-register)) + ((markerp val) + (let ((buf (marker-buffer val))) + (if (null buf) + (list "a marker in no buffer") + (list (concat + "a buffer position:" + (buffer-name buf) + ", position " + (int-to-string (marker-position val))) + 'jump-to-register + 'insert-register)))) + ((and (consp val) (window-configuration-p (car val))) + (list "window configuration." + 'jump-to-register)) + ((and (vectorp val) + (fboundp 'undo-tree-register-data-p) + (undo-tree-register-data-p (elt val 1))) + (list + "Undo-tree entry." + 'undo-tree-restore-state-from-register)) + ((or (and (vectorp val) (eq 'registerv (aref val 0))) + (and (consp val) (frame-configuration-p (car val)))) + (list "frame configuration." + 'jump-to-register)) + ((and (consp val) (eq (car val) 'file)) + (list (concat "file:" + (prin1-to-string (cdr val)) + ".") + 'jump-to-register)) + ((and (consp val) (eq (car val) 'file-query)) + (list (concat "file:a file-query reference: file " + (car (cdr val)) + ", position " + (int-to-string (car (cdr (cdr val)))) + ".") + 'jump-to-register)) + ((consp val) + (let ((lines (format "%4d" (length val)))) + (list (format "%s: %s\n" lines + (truncate-string-to-width + (mapconcat 'identity (list (car val)) + "^J") + (- (window-width) 15))) + 'insert-register))) + ((stringp val) + (list + (concat (substring-no-properties + val 0 (min (length val) helm-register-max-offset)) + (if (> (length val) helm-register-max-offset) + "[...]" "")) + 'insert-register + 'kill-new + 'append-to-register + 'prepend-to-register))) + unless (null string-actions) ; Fix Issue #1107. + collect (cons (format "Register %3s:\n %s" key (car string-actions)) + (cons char (cdr string-actions))))) + +(defun helm-register-action-transformer (actions register-and-functions) + "Decide actions by the contents of register." + (cl-loop with func-actions = + '((insert-register + "Insert Register" . + (lambda (c) (insert-register (car c)))) + (kill-new + "Kill Register" . + (lambda (c) (with-temp-buffer + (insert-register (car c)) + (kill-new (buffer-string))))) + (jump-to-register + "Jump to Register" . + (lambda (c) (jump-to-register (car c)))) + (append-to-register + "Append Region to Register" . + (lambda (c) (append-to-register + (car c) (region-beginning) (region-end)))) + (prepend-to-register + "Prepend Region to Register" . + (lambda (c) (prepend-to-register + (car c) (region-beginning) (region-end)))) + (increment-register + "Increment Prefix Arg to Register" . + (lambda (c) (increment-register + helm-current-prefix-arg (car c)))) + (undo-tree-restore-state-from-register + "Restore Undo-tree register" . + (lambda (c) (and (fboundp 'undo-tree-restore-state-from-register) + (undo-tree-restore-state-from-register (car c)))))) + for func in (cdr register-and-functions) + when (assq func func-actions) + collect (cdr it) into transformer-actions + finally return (append transformer-actions actions))) + +;;;###autoload +(defun helm-mark-ring () + "Preconfigured `helm' for `helm-source-mark-ring'." + (interactive) + (helm :sources 'helm-source-mark-ring + :resume 'noresume + :buffer "*helm mark*")) + +;;;###autoload +(defun helm-global-mark-ring () + "Preconfigured `helm' for `helm-source-global-mark-ring'." + (interactive) + (helm :sources 'helm-source-global-mark-ring + :resume 'noresume + :buffer "*helm global mark*")) + +;;;###autoload +(defun helm-all-mark-rings () + "Preconfigured `helm' for `helm-source-global-mark-ring' and \ +`helm-source-mark-ring'." + (interactive) + (helm :sources '(helm-source-mark-ring + helm-source-global-mark-ring) + :resume 'noresume + :buffer "*helm mark ring*")) + +;;;###autoload +(defun helm-register () + "Preconfigured `helm' for Emacs registers." + (interactive) + (helm :sources 'helm-source-register + :resume 'noresume + :buffer "*helm register*")) + +;;;###autoload +(defun helm-show-kill-ring () + "Preconfigured `helm' for `kill-ring'. +It is drop-in replacement of `yank-pop'. + +First call open the kill-ring browser, next calls move to next line." + (interactive) + (setq helm-kill-ring--truncated-flag nil) + (let ((enable-recursive-minibuffers t)) + (helm :sources helm-source-kill-ring + :buffer "*helm kill ring*" + :resume 'noresume + :allow-nest t))) + +;;;###autoload +(defun helm-execute-kmacro () + "Preconfigured helm for keyboard macros. +Define your macros with `f3' and `f4'. +See (info \"(emacs) Keyboard Macros\") for detailed infos. +This command is useful when used with persistent action." + (interactive) + (let ((helm-quit-if-no-candidate + (lambda () (message "No kbd macro has been defined")))) + (helm :sources + (helm-build-sync-source "Kmacro" + :candidates (lambda () + (helm-fast-remove-dups + (cons (kmacro-ring-head) + kmacro-ring) + :test 'equal)) + :multiline t + :candidate-transformer + (lambda (candidates) + (cl-loop for c in candidates collect + (propertize (help-key-description (car c) nil) + 'helm-realvalue c))) + :persistent-help "Execute kmacro" + :help-message 'helm-kmacro-help-message + :action + (helm-make-actions + "Execute kmacro (`C-u ' to execute times)" + 'helm-kbd-macro-execute + "Concat marked macros" + 'helm-kbd-macro-concat-macros + "Delete marked macros" + 'helm-kbd-macro-delete-macro + "Edit marked macro" + 'helm-kbd-macro-edit-macro) + :group 'helm-ring) + :buffer "*helm kmacro*"))) + +(defun helm-kbd-macro-execute (candidate) + ;; Move candidate on top of list for next use. + (setq kmacro-ring (delete candidate kmacro-ring)) + (kmacro-push-ring) + (kmacro-split-ring-element candidate) + (kmacro-exec-ring-item + candidate helm-current-prefix-arg)) + +(defun helm-kbd-macro-concat-macros (_candidate) + (let ((mkd (helm-marked-candidates))) + (when (cdr mkd) + (kmacro-push-ring) + (setq last-kbd-macro + (mapconcat 'identity + (cl-loop for km in mkd + if (vectorp km) + append (cl-loop for k across km collect + (key-description (vector k))) + into result + else collect (car km) into result + finally return result) + ""))))) + +(defun helm-kbd-macro-delete-macro (_candidate) + (let ((mkd (helm-marked-candidates))) + (kmacro-push-ring) + (cl-loop for km in mkd + do (setq kmacro-ring (delete km kmacro-ring))) + (kmacro-pop-ring1))) + +(defun helm-kbd-macro-edit-macro (candidate) + (kmacro-push-ring) + (setq kmacro-ring (delete candidate kmacro-ring)) + (kmacro-split-ring-element candidate) + (kmacro-edit-macro)) + +(provide 'helm-ring) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-ring.el ends here diff --git a/elpa/helm-20191031.839/helm-semantic.el b/elpa/helm-20191031.839/helm-semantic.el new file mode 100644 index 00000000..f5691244 --- /dev/null +++ b/elpa/helm-20191031.839/helm-semantic.el @@ -0,0 +1,236 @@ +;;; helm-semantic.el --- Helm interface for Semantic -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2017 Daniel Hackney +;; 2012 ~ 2019 Thierry Volpiatto + +;; Author: Daniel Hackney + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Commentary: + +;; Uses `candidates-in-buffer' for speed. + +;;; Code: + +(require 'cl-lib) +(require 'semantic) +(require 'helm-help) +(require 'helm-imenu) + +(declare-function pulse-momentary-highlight-one-line "pulse.el" (point &optional face)) + +(defgroup helm-semantic nil + "Semantic tags related libraries and applications for helm." + :group 'helm) + +(defcustom helm-semantic-display-style + '((python-mode . semantic-format-tag-summarize) + (c-mode . semantic-format-tag-concise-prototype-c-mode) + (emacs-lisp-mode . semantic-format-tag-abbreviate-emacs-lisp-mode)) + "Function to present a semantic tag according to `major-mode'. + +It is an alist where the `car' of each element is a `major-mode' and +the `cdr' a `semantic-format-tag-*' function. + +If no function is found for current `major-mode', fall back to +`semantic-format-tag-summarize' default function. + +You can have more or less informations depending of the `semantic-format-tag-*' +function you choose. + +All the supported functions are prefixed with \"semantic-format-tag-\", +you have completion on these functions with `C-M i' in the customize interface." + :group 'helm-semantic + :type '(alist :key-type symbol :value-type symbol)) + +;;; keymap +(defvar helm-semantic-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + map)) + +(defcustom helm-semantic-lynx-style-map nil + "Use Arrow keys to jump to occurences." + :group 'helm-semantic + :type 'boolean + :set (lambda (var val) + (set var val) + (if val + (progn + (define-key helm-semantic-map (kbd "") 'helm-execute-persistent-action) + (define-key helm-semantic-map (kbd "") 'helm-maybe-exit-minibuffer)) + (define-key helm-semantic-map (kbd "") nil) + (define-key helm-semantic-map (kbd "") nil)))) + +;; Internals vars +(defvar helm-semantic--tags-cache nil) + +(defun helm-semantic--fetch-candidates (tags depth &optional class) + "Write the contents of TAGS to the current buffer." + (let ((class class) cur-type + (stylefn (or (with-helm-current-buffer + (assoc-default major-mode helm-semantic-display-style)) + #'semantic-format-tag-summarize))) + (cl-dolist (tag tags) + (when (listp tag) + (cl-case (setq cur-type (semantic-tag-class tag)) + ((function variable type) + (let ((spaces (make-string (* depth 2) ?\s)) + (type-p (eq cur-type 'type))) + (unless (and (> depth 0) (not type-p)) + (setq class nil)) + (insert + (if (and class (not type-p)) + (format "%s%s(%s) " + spaces (if (< depth 2) "" "├►") class) + spaces) + ;; Save the tag for later + (propertize (funcall stylefn tag nil t) + 'semantic-tag tag) + "\n") + (and type-p (setq class (car tag))) + ;; Recurse to children + (unless (eq cur-type 'function) + (helm-semantic--fetch-candidates + (semantic-tag-components tag) (1+ depth) class)))) + + ;; Don't do anything with packages or includes for now + ((package include) + (insert + (propertize (funcall stylefn tag nil t) + 'semantic-tag tag) + "\n") + ) + ;; Catch-all + (t)))))) + +(defun helm-semantic-default-action (_candidate &optional persistent) + ;; By default, helm doesn't pass on the text properties of the selection. + ;; Fix this. + (helm-log-run-hook 'helm-goto-line-before-hook) + (with-current-buffer helm-buffer + (when (looking-at " ") + (goto-char (next-single-property-change + (point-at-bol) 'semantic-tag nil (point-at-eol)))) + (let ((tag (get-text-property (point) 'semantic-tag))) + (semantic-go-to-tag tag) + (unless persistent + (pulse-momentary-highlight-one-line (point)))))) + +(defun helm-semantic--maybe-set-needs-update () + (with-helm-current-buffer + (when (semantic-parse-tree-needs-update-p) + (semantic-parse-tree-set-needs-update)))) + +(defvar helm-source-semantic nil) + +(defclass helm-semantic-source (helm-source-in-buffer) + ((init :initform (lambda () + (helm-semantic--maybe-set-needs-update) + (setq helm-semantic--tags-cache (semantic-fetch-tags)) + (with-current-buffer (helm-candidate-buffer 'global) + (let ((major-mode (with-helm-current-buffer major-mode))) + (helm-semantic--fetch-candidates helm-semantic--tags-cache 0))))) + (get-line :initform 'buffer-substring) + (persistent-help :initform "Show this entry") + (keymap :initform 'helm-semantic-map) + (help-message :initform 'helm-semantic-help-message) + (persistent-action :initform (lambda (elm) + (helm-semantic-default-action elm t) + (helm-highlight-current-line))) + (action :initform 'helm-semantic-default-action))) + +(defcustom helm-semantic-fuzzy-match nil + "Enable fuzzy matching in `helm-source-semantic'." + :group 'helm-semantic + :type 'boolean + :set (lambda (var val) + (set var val) + (setq helm-source-semantic + (helm-make-source "Semantic Tags" 'helm-semantic-source + :fuzzy-match helm-semantic-fuzzy-match)))) + +;;;###autoload +(defun helm-semantic (arg) + "Preconfigured `helm' for `semantic'. +If ARG is supplied, pre-select symbol at point instead of current" + (interactive "P") + (let ((tag (helm-aif (car (semantic-current-tag-parent)) + (let ((curtag (car (semantic-current-tag)))) + (if (string= it curtag) + (format "\\_<%s\\_>" curtag) + (cons (format "\\_<%s\\_>" it) + (format "\\_<%s\\_>" curtag)))) + (format "\\_<%s\\_>" (car (semantic-current-tag)))))) + (unless helm-source-semantic + (setq helm-source-semantic + (helm-make-source "Semantic Tags" 'helm-semantic-source + :fuzzy-match helm-semantic-fuzzy-match))) + (helm :sources 'helm-source-semantic + :candidate-number-limit 9999 + :preselect (if arg + (thing-at-point 'symbol) + tag) + :buffer "*helm semantic*"))) + +;;;###autoload +(defun helm-semantic-or-imenu (arg) + "Preconfigured helm for `semantic' or `imenu'. +If ARG is supplied, pre-select symbol at point instead of current +semantic tag in scope. + +If `semantic-mode' is active in the current buffer, then use +semantic for generating tags, otherwise fall back to `imenu'. +Fill in the symbol at point by default." + (interactive "P") + (unless helm-source-semantic + (setq helm-source-semantic + (helm-make-source "Semantic Tags" 'helm-semantic-source + :fuzzy-match helm-semantic-fuzzy-match))) + (unless helm-source-imenu + (setq helm-source-imenu + (helm-make-source "Imenu" 'helm-imenu-source + :fuzzy-match helm-imenu-fuzzy-match))) + (let* ((source (if (semantic-active-p) + 'helm-source-semantic + 'helm-source-imenu)) + (imenu-p (eq source 'helm-source-imenu)) + (imenu-auto-rescan imenu-p) + (str (thing-at-point 'symbol)) + (helm-execute-action-at-once-if-one + (and imenu-p + helm-imenu-execute-action-at-once-if-one)) + (tag (helm-aif (car (semantic-current-tag-parent)) + (let ((curtag (car (semantic-current-tag)))) + (if (string= it curtag) + (format "\\_<%s\\_>" curtag) + (cons (format "\\_<%s\\_>" it) + (format "\\_<%s\\_>" curtag)))) + (format "\\_<%s\\_>" (car (semantic-current-tag)))))) + (helm :sources source + :candidate-number-limit 9999 + :default (and imenu-p (list (concat "\\_<" (and str (regexp-quote str)) "\\_>") str)) + :preselect (if (or arg imenu-p) str tag) + :buffer "*helm semantic/imenu*"))) + +(provide 'helm-semantic) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-semantic.el ends here diff --git a/elpa/helm-20191031.839/helm-shell.el b/elpa/helm-20191031.839/helm-shell.el new file mode 100644 index 00000000..5f946dc5 --- /dev/null +++ b/elpa/helm-20191031.839/helm-shell.el @@ -0,0 +1,44 @@ +;;; helm-shell.el --- Shell prompt navigation for helm. -*- lexical-binding: t -*- + +;; Copyright (C) 2019 Pierre Neidhardt + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Commentary: +;; +;; This is superseded by helm-comint.el. + +;;; Code: +(require 'cl-lib) +(require 'helm) +(require 'helm-lib) +(require 'helm-help) +(require 'helm-elisp) +(require 'helm-comint) + +;;;###autoload +(defalias 'helm-shell-prompts 'helm-comint-prompts) + +;;;###autoload +(defalias 'helm-shell-prompts-all 'helm-comint-prompts-all) + +(provide 'helm-shell) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-shell ends here diff --git a/elpa/helm-20191031.839/helm-sys.el b/elpa/helm-20191031.839/helm-sys.el new file mode 100644 index 00000000..cfe015ec --- /dev/null +++ b/elpa/helm-20191031.839/helm-sys.el @@ -0,0 +1,459 @@ +;;; helm-sys.el --- System related functions for helm. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'cl-lib) +(require 'helm) +(require 'helm-help) +(require 'helm-utils) + + +(defgroup helm-sys nil + "System related helm library." + :group 'helm) + +(defface helm-top-columns + '((t :inherit helm-header)) + "Face for helm help string in minibuffer." + :group 'helm-sys) + + +(defcustom helm-top-command + (cl-case system-type + (darwin "env COLUMNS=%s ps -axo pid,user,pri,nice,ucomm,tty,start_time,vsz,%%cpu,%%mem,etime,command") + (t "env COLUMNS=%s top -b -n 1")) + "Top command used to display output of top. +A format string where %s will be replaced with `frame-width'. + +To use 'top' command, a version supporting batch mode (-b option) is needed. +On Mac OSX 'top' command doesn't support this, so ps command +is used instead by default. +Normally 'top' command output have 12 columns, but in some versions you may +have less than this, so you can either customize top to use 12 columns with the +interactives 'f' and 'W' commands of top, or modify +`helm-top-sort-columns-alist' to fit with the number of columns +your 'top' command is using. + +If you modify 'ps' command be sure that 'pid' comes in first +and \"env COLUMNS=%s\" is specified at beginning of command. +Ensure also that no elements contain spaces (e.g use start_time and not start). +Same as for 'top' you can customize `helm-top-sort-columns-alist' to make sort commands +working properly according to your settings." + :group 'helm-sys + :type 'string) + +(defcustom helm-top-sort-columns-alist '((com . 11) + (mem . 9) + (cpu . 8) + (user . 1)) + "Allow defining which column to use when sorting output of top/ps command. +Only com, mem, cpu and user are sorted, so no need to put something else there, +it will have no effect. +Note that column numbers are counted from zero, i.e column 1 is the nth 0 column." + :group 'helm-sys + :type '(alist :key-type symbol :value-type (integer :tag "Column number"))) + +(defcustom helm-top-poll-delay 1.5 + "Helm top poll after this delay when `helm-top-poll-mode' is enabled. +The minimal delay allowed is 1.5, if less than this helm-top will use 1.5." + :group 'helm-sys + :type 'float) + +(defcustom helm-top-poll-delay-post-command 1.0 + "Helm top stop polling during this delay. +This delay is additioned to `helm-top-poll-delay' after emacs stop +being idle." + :group 'helm-sys + :type 'float) + +(defcustom helm-top-poll-preselection 'linum + "Stay on same line or follow candidate when `helm-top-poll' update display. +Possible values are 'candidate or 'linum. +This affect also sorting functions in the same way." + :group'helm-sys + :type '(radio :tag "Preferred preselection action for helm-top" + (const :tag "Follow candidate" candidate) + (const :tag "Stay on same line" linum))) + +;;; Top (process) +;; +;; +(defvar helm-top-sort-fn nil) +(defvar helm-top-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "M-P") 'helm-top-run-sort-by-cpu) + (define-key map (kbd "M-C") 'helm-top-run-sort-by-com) + (define-key map (kbd "M-M") 'helm-top-run-sort-by-mem) + (define-key map (kbd "M-U") 'helm-top-run-sort-by-user) + map)) + +(defvar helm-top-after-init-hook nil + "Local hook for helm-top.") + +(defvar helm-top--poll-timer nil) + +(defun helm-top-poll (&optional no-update delay) + (when helm-top--poll-timer + (cancel-timer helm-top--poll-timer)) + (condition-case nil + (progn + (when (and (helm--alive-p) (null no-update)) + ;; Fix quitting while process is running + ;; by binding `with-local-quit' in init function + ;; Issue #1521. + (helm-force-update + (cl-ecase helm-top-poll-preselection + (candidate (replace-regexp-in-string + "[0-9]+" "[0-9]+" + (regexp-quote (helm-get-selection nil t)))) + (linum `(lambda () + (goto-char (point-min)) + (forward-line ,(helm-candidate-number-at-point))))))) + (setq helm-top--poll-timer + (run-with-idle-timer + (helm-aif (current-idle-time) + (time-add it (seconds-to-time + (or delay (helm-top--poll-delay)))) + (or delay (helm-top--poll-delay))) + nil + 'helm-top-poll))) + (quit (cancel-timer helm-top--poll-timer)))) + +(defun helm-top--poll-delay () + (max 1.5 helm-top-poll-delay)) + +(defun helm-top-poll-no-update () + (helm-top-poll t (+ (helm-top--poll-delay) + helm-top-poll-delay-post-command))) + +(defun helm-top-initialize-poll-hooks () + ;; When emacs is idle during say 20s + ;; the idle timer will run in 20+1.5 s. + ;; This is fine when emacs stays idle, because the next timer + ;; will run at 21.5+1.5 etc... so the display will be updated + ;; at every 1.5 seconds. + ;; But as soon as emacs looses its idleness, the next update + ;; will occur at say 21+1.5 s, so we have to reinitialize + ;; the timer at 0+1.5. + (add-hook 'post-command-hook 'helm-top-poll-no-update) + (add-hook 'focus-in-hook 'helm-top-poll-no-update)) + +;;;###autoload +(define-minor-mode helm-top-poll-mode + "Refresh automatically helm top buffer once enabled." + :group 'helm-top + :global t + (if helm-top-poll-mode + (progn + (add-hook 'helm-top-after-init-hook 'helm-top-poll-no-update) + (add-hook 'helm-top-after-init-hook 'helm-top-initialize-poll-hooks)) + (remove-hook 'helm-top-after-init-hook 'helm-top-poll-no-update) + (remove-hook 'helm-top-after-init-hook 'helm-top-initialize-poll-hooks))) + +(defvar helm-source-top + (helm-build-in-buffer-source "Top" + :header-name (lambda (name) + (concat name (if helm-top-poll-mode + " (auto updating)" + " (Press C-c C-u to refresh)"))) + :init #'helm-top-init + :after-init-hook 'helm-top-after-init-hook + :cleanup (lambda () + (when helm-top--poll-timer + (cancel-timer helm-top--poll-timer)) + (remove-hook 'post-command-hook 'helm-top-poll-no-update) + (remove-hook 'focus-in-hook 'helm-top-poll-no-update)) + :display-to-real #'helm-top-display-to-real + :persistent-action '(helm-top-sh-persistent-action . never-split) + :persistent-help "SIGTERM" + :help-message 'helm-top-help-message + :mode-line 'helm-top-mode-line + :follow 'never + :keymap helm-top-map + :filtered-candidate-transformer #'helm-top-sort-transformer + :action-transformer #'helm-top-action-transformer + :group 'helm-sys)) + +(defvar helm-top--line nil) +(defun helm-top-transformer (candidates _source) + "Transformer for `helm-top'. +Return empty string for non--valid candidates." + (cl-loop for disp in candidates collect + (cond ((string-match "^ *[0-9]+" disp) disp) + ((string-match "^ *PID" disp) + (setq helm-top--line (cons (propertize disp 'face 'helm-top-columns) ""))) + (t (cons disp ""))) + into lst + finally return (or (member helm-top--line lst) + (cons helm-top--line lst)))) + +(defun helm-top--skip-top-line () + (let* ((src (helm-get-current-source)) + (src-name (assoc-default 'name src))) + (helm-aif (and (stringp src-name) + (string= src-name "Top") + (helm-get-selection nil t src)) + (when (string-match-p "^ *PID" it) + (helm-next-line))))) + +(defun helm-top-action-transformer (actions _candidate) + "Action transformer for `top'. +Show actions only on line starting by a PID." + (let ((disp (helm-get-selection nil t))) + (cond ((string-match "\\` *[0-9]+" disp) + (list '("kill (SIGTERM)" . (lambda (_pid) + (helm-top-sh "TERM" (helm-top--marked-pids)))) + '("kill (SIGKILL)" . (lambda (_pid) + (helm-top-sh "KILL" (helm-top--marked-pids)))) + '("kill (SIGINT)" . (lambda (_pid) + (helm-top-sh "INT" (helm-top--marked-pids)))) + '("kill (Choose signal)" + . (lambda (_pid) + (let ((pids (helm-top--marked-pids))) + (helm-top-sh + (helm-comp-read (format "Kill %d pids with signal: " + (length pids)) + '("ALRM" "HUP" "INT" "KILL" "PIPE" "POLL" + "PROF" "TERM" "USR1" "USR2" "VTALRM" + "STKFLT" "PWR" "WINCH" "CHLD" "URG" + "TSTP" "TTIN" "TTOU" "STOP" "CONT" + "ABRT" "FPE" "ILL" "QUIT" "SEGV" + "TRAP" "SYS" "EMT" "BUS" "XCPU" "XFSZ") + :must-match t) + pids)))))) + (t actions)))) + +(defun helm-top--marked-pids () + (helm-remove-if-not-match "\\`[0-9]+\\'" (helm-marked-candidates))) + +(defun helm-top-sh (sig pids) + "Run kill shell command with signal SIG on PIDS for `helm-top'." + (message "kill -%s %s exited with status %s" + sig (mapconcat 'identity pids " ") + (apply #'call-process + "kill" nil nil nil (format "-%s" sig) pids))) + +(defun helm-top-sh-persistent-action (pid) + (helm-top-sh "TERM" (list pid)) + (helm-delete-current-selection)) + +(defun helm-top-init () + "Insert output of top command in candidate buffer." + (with-local-quit + (unless helm-top-sort-fn (helm-top-set-mode-line "CPU")) + (with-current-buffer (helm-candidate-buffer 'global) + (call-process-shell-command + (format helm-top-command (frame-width)) + nil (current-buffer))))) + +(defun helm-top-display-to-real (line) + "Return pid only from LINE." + (car (split-string line))) + +;; Sort top command + +(defun helm-top-set-mode-line (str) + (if (string-match "Sort:\\[\\(.*\\)\\] " helm-top-mode-line) + (setq helm-top-mode-line (replace-match str nil nil helm-top-mode-line 1)) + (setq helm-top-mode-line (concat (format "Sort:[%s] " str) helm-top-mode-line)))) + +(defun helm-top-sort-transformer (candidates source) + (helm-top-transformer + (if helm-top-sort-fn + (cl-loop for c in candidates + if (string-match "^ *[0-9]+" c) + collect c into pid-cands + else collect c into header-cands + finally return (append + header-cands + (sort pid-cands helm-top-sort-fn))) + candidates) + source)) + +(defun helm-top-sort-by-com (s1 s2) + (let* ((split-1 (split-string s1)) + (split-2 (split-string s2)) + (col (cdr (assq 'com helm-top-sort-columns-alist))) + (com-1 (nth col split-1)) + (com-2 (nth col split-2))) + (string< com-1 com-2))) + +(defun helm-top-sort-by-mem (s1 s2) + (let* ((split-1 (split-string s1)) + (split-2 (split-string s2)) + (col (cdr (assq 'mem helm-top-sort-columns-alist))) + (mem-1 (string-to-number (nth col split-1))) + (mem-2 (string-to-number (nth col split-2)))) + (> mem-1 mem-2))) + +(defun helm-top-sort-by-cpu (s1 s2) + (let* ((split-1 (split-string s1)) + (split-2 (split-string s2)) + (col (cdr (assq 'cpu helm-top-sort-columns-alist))) + (cpu-1 (string-to-number (nth col split-1))) + (cpu-2 (string-to-number (nth col split-2)))) + (> cpu-1 cpu-2))) + +(defun helm-top-sort-by-user (s1 s2) + (let* ((split-1 (split-string s1)) + (split-2 (split-string s2)) + (col (cdr (assq 'user helm-top-sort-columns-alist))) + (user-1 (nth col split-1)) + (user-2 (nth col split-2))) + (string< user-1 user-2))) + +(defun helm-top--preselect-fn () + (if (eq helm-top-poll-preselection 'linum) + `(lambda () + (goto-char (point-min)) + (forward-line ,(helm-candidate-number-at-point))) + (replace-regexp-in-string + "[0-9]+" "[0-9]+" + (regexp-quote (helm-get-selection nil t))))) + +(defun helm-top-run-sort-by-com () + (interactive) + (helm-top-set-mode-line "COM") + (setq helm-top-sort-fn 'helm-top-sort-by-com) + (helm-update (helm-top--preselect-fn))) + +(defun helm-top-run-sort-by-cpu () + (interactive) + (helm-top-set-mode-line "CPU") + ;; Force sorting by CPU even if some versions of top are using by + ;; default CPU sorting (Issue #1908). + (setq helm-top-sort-fn 'helm-top-sort-by-cpu) + (helm-update (helm-top--preselect-fn))) + +(defun helm-top-run-sort-by-mem () + (interactive) + (helm-top-set-mode-line "MEM") + (setq helm-top-sort-fn 'helm-top-sort-by-mem) + (helm-update (helm-top--preselect-fn))) + +(defun helm-top-run-sort-by-user () + (interactive) + (helm-top-set-mode-line "USER") + (setq helm-top-sort-fn 'helm-top-sort-by-user) + (helm-update (helm-top--preselect-fn))) + + +;;; X RandR resolution change +;; +;; +;;; FIXME I do not care multi-display. + +(defun helm-xrandr-info () + "Return a pair with current X screen number and current X display name." + (with-temp-buffer + (call-process "xrandr" nil (current-buffer) nil + "--current") + (let (screen output) + (goto-char (point-min)) + (save-excursion + (when (re-search-forward "\\(^Screen \\)\\([0-9]\\):" nil t) + (setq screen (match-string 2)))) + (when (re-search-forward "^\\(.*\\) connected" nil t) + (setq output (match-string 1))) + (list screen output)))) + +(defun helm-xrandr-screen () + "Return current X screen number." + (car (helm-xrandr-info))) + +(defun helm-xrandr-output () + "Return current X display name." + (cadr (helm-xrandr-info))) + +(defvar helm-source-xrandr-change-resolution + (helm-build-sync-source "Change Resolution" + :candidates + (lambda () + (with-temp-buffer + (call-process "xrandr" nil (current-buffer) nil + "--screen" (helm-xrandr-screen) "-q") + (goto-char 1) + (cl-loop while (re-search-forward " \\([0-9]+x[0-9]+\\)" nil t) + for mode = (match-string 1) + unless (member mode modes) + collect mode into modes + finally return modes))) + :action + (helm-make-actions "Change Resolution" + (lambda (mode) + (call-process "xrandr" nil nil nil + "--screen" (helm-xrandr-screen) + "--output" (helm-xrandr-output) + "--mode" mode))))) + + +;;; Emacs process +;; +;; +(defvar helm-source-emacs-process + (helm-build-sync-source "Emacs Process" + :init (lambda () + (let (tabulated-list-use-header-line) + (list-processes--refresh))) + :candidates (lambda () (mapcar #'process-name (process-list))) + :persistent-action (lambda (elm) + (delete-process (get-process elm)) + (helm-delete-current-selection)) + :persistent-help "Kill Process" + :action (helm-make-actions "Kill Process" + (lambda (_elm) + (cl-loop for p in (helm-marked-candidates) + do (delete-process (get-process p))))))) + + +;;;###autoload +(defun helm-top () + "Preconfigured `helm' for top command." + (interactive) + (add-hook 'helm-after-update-hook 'helm-top--skip-top-line) + (unwind-protect + (helm :sources 'helm-source-top + :buffer "*helm top*" :full-frame t + :candidate-number-limit 9999 + :preselect "^\\s-*[0-9]+" + :truncate-lines helm-show-action-window-other-window) + (remove-hook 'helm-after-update-hook 'helm-top--skip-top-line))) + +;;;###autoload +(defun helm-list-emacs-process () + "Preconfigured `helm' for emacs process." + (interactive) + (helm-other-buffer 'helm-source-emacs-process "*helm process*")) + +;;;###autoload +(defun helm-xrandr-set () + "Preconfigured helm for xrandr." + (interactive) + (helm :sources 'helm-source-xrandr-change-resolution + :buffer "*helm xrandr*")) + +(provide 'helm-sys) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-sys.el ends here diff --git a/elpa/helm-20191031.839/helm-tags.el b/elpa/helm-20191031.839/helm-tags.el new file mode 100644 index 00000000..782e87b4 --- /dev/null +++ b/elpa/helm-20191031.839/helm-tags.el @@ -0,0 +1,348 @@ +;;; helm-tags.el --- Helm for Etags. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'cl-lib) +(require 'helm) +(require 'helm-help) +(require 'helm-utils) +(require 'helm-grep) + + +(defgroup helm-tags nil + "Tags related Applications and libraries for Helm." + :group 'helm) + +(defcustom helm-etags-tag-file-name "TAGS" + "Etags tag file name." + :type 'string + :group 'helm-tags) + +(defcustom helm-etags-tag-file-search-limit 10 + "The limit level of directory to search tag file. +Don't search tag file deeply if outside this value." + :type 'number + :group 'helm-tags) + +(defcustom helm-etags-match-part-only 'tag + "Allow choosing the tag part of CANDIDATE in `helm-source-etags-select'. +A tag looks like this: + filename: \(defun foo +You can choose matching against the tag part (i.e \"(defun foo\"), +or against the whole candidate (i.e \"(filename:5:(defun foo\")." + :type '(choice + (const :tag "Match only tag" tag) + (const :tag "Match all file+tag" all)) + :group 'helm-tags) + +(defcustom helm-etags-execute-action-at-once-if-one t + "Whether to jump straight to the selected tag if there's only +one match." + :type 'boolean + :group 'helm-tags) + + +(defgroup helm-tags-faces nil + "Customize the appearance of helm-tags faces." + :prefix "helm-" + :group 'helm-tags + :group 'helm-faces) + +(defface helm-etags-file + '((t (:foreground "Lightgoldenrod4" + :underline t))) + "Face used to highlight etags filenames." + :group 'helm-tags-faces) + + +;;; Etags +;; +;; +(defun helm-etags-run-switch-other-window () + "Run switch to other window action from `helm-source-etags-select'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action + (lambda (c) + (helm-etags-action-goto 'find-file-other-window c))))) +(put 'helm-etags-run-switch-other-window 'helm-only t) + +(defun helm-etags-run-switch-other-frame () + "Run switch to other frame action from `helm-source-etags-select'." + (interactive) + (with-helm-alive-p + (helm-exit-and-execute-action + (lambda (c) + (helm-etags-action-goto 'find-file-other-frame c))))) +(put 'helm-etags-run-switch-other-frame 'helm-only t) + +(defvar helm-etags-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "M-") 'helm-goto-next-file) + (define-key map (kbd "M-") 'helm-goto-precedent-file) + (define-key map (kbd "C-c o") 'helm-etags-run-switch-other-window) + (define-key map (kbd "C-c C-o") 'helm-etags-run-switch-other-frame) + map) + "Keymap used in Etags.") + +(defvar helm-etags-mtime-alist nil + "Store the last modification time of etags files here.") +(defvar helm-etags-cache (make-hash-table :test 'equal) + "Cache content of etags files used here for faster access.") + +(defun helm-etags-get-tag-file (&optional directory) + "Return the path of etags file if found. +Lookes recursively in parents directorys for a +`helm-etags-tag-file-name' file." + ;; Get tag file from `default-directory' or upper directory. + (let ((current-dir (helm-etags-find-tag-file-directory + (or directory default-directory)))) + ;; Return nil if not find tag file. + (when current-dir + (expand-file-name helm-etags-tag-file-name current-dir)))) + +(defun helm-etags-all-tag-files () + "Return files from the following sources; + 1) An automatically located file in the parent directories, by `helm-etags-get-tag-file'. + 2) `tags-file-name', which is commonly set by `find-tag' command. + 3) `tags-table-list' which is commonly set by `visit-tags-table' command." + (helm-fast-remove-dups + (delq nil + (append (list (helm-etags-get-tag-file) + tags-file-name) + tags-table-list)) + :test 'equal)) + +(defun helm-etags-find-tag-file-directory (current-dir) + "Try to find the directory containing tag file. +If not found in CURRENT-DIR search in upper directory." + (let ((file-exists? (lambda (dir) + (let ((tag-path (expand-file-name + helm-etags-tag-file-name dir))) + (and (stringp tag-path) + (file-regular-p tag-path) + (file-readable-p tag-path)))))) + (cl-loop with count = 0 + until (funcall file-exists? current-dir) + ;; Return nil if outside the value of + ;; `helm-etags-tag-file-search-limit'. + if (= count helm-etags-tag-file-search-limit) + do (cl-return nil) + ;; Or search upper directories. + else + do (cl-incf count) + (setq current-dir (expand-file-name (concat current-dir "../"))) + finally return current-dir))) + +(defun helm-etags-get-header-name (_x) + "Create header name for this helm etags session." + (concat "Etags in " + (with-helm-current-buffer + (helm-etags-get-tag-file)))) + +(defun helm-etags-create-buffer (file) + "Create the `helm-buffer' based on contents of etags tag FILE." + (let* (max + (split (with-temp-buffer + (insert-file-contents file) + (prog1 + (split-string (buffer-string) "\n" 'omit-nulls) + (setq max (line-number-at-pos (point-max)))))) + (progress-reporter (make-progress-reporter "Loading tag file..." 0 max))) + (cl-loop + with fname + with cand + for i in split for count from 0 + for elm = (unless (string-match "^\x0c" i) ;; "^L" + (helm-aif (string-match "\177" i) ;; "^?" + (substring i 0 it) + i)) + for linum = (when (string-match "[0-9]+,?[0-9]*$" i) + (car (split-string (match-string 0 i) ","))) + do (cond ((and elm (string-match "^\\([^,]+\\),[0-9]+$" elm)) + (setq fname (propertize (match-string 1 elm) + 'face 'helm-etags-file))) + (elm (setq cand (format "%s:%s:%s" fname linum elm))) + (t (setq cand nil))) + when cand do (progn + (insert (propertize (concat cand "\n") 'linum linum)) + (progress-reporter-update progress-reporter count))))) + +(defun helm-etags-init () + "Feed `helm-buffer' using `helm-etags-cache' or tag file. +If no entry in cache, create one." + (let ((tagfiles (helm-etags-all-tag-files))) + (when tagfiles + (with-current-buffer (helm-candidate-buffer 'global) + (dolist (f tagfiles) + (helm-aif (gethash f helm-etags-cache) + ;; An entry is present in cache, insert it. + (insert it) + ;; No entry, create a new buffer using content of tag file (slower). + (helm-etags-create-buffer f) + ;; Store content of buffer in cache. + (puthash f (buffer-string) helm-etags-cache) + ;; Store or set the last modification of tag file. + (helm-aif (assoc f helm-etags-mtime-alist) + ;; If an entry exists modify it. + (setcdr it (helm-etags-mtime f)) + ;; No entry create a new one. + (cl-pushnew (cons f (helm-etags-mtime f)) + helm-etags-mtime-alist + :test 'equal)))))))) + +(defvar helm-source-etags-select nil + "Helm source for Etags.") + +(defun helm-etags-build-source () + (helm-build-in-buffer-source "Etags" + :header-name 'helm-etags-get-header-name + :init 'helm-etags-init + :get-line 'buffer-substring + :match-part (lambda (candidate) + ;; Match only the tag part of CANDIDATE + ;; and not the filename. + (cl-case helm-etags-match-part-only + (tag (cl-caddr (helm-grep-split-line candidate))) + (t candidate))) + :fuzzy-match helm-etags-fuzzy-match + :help-message 'helm-etags-help-message + :keymap helm-etags-map + :action '(("Go to tag" . (lambda (c) + (helm-etags-action-goto 'find-file c))) + ("Go to tag in other window" . (lambda (c) + (helm-etags-action-goto + 'find-file-other-window + c))) + ("Go to tag in other frame" . (lambda (c) + (helm-etags-action-goto + 'find-file-other-frame + c)))) + :group 'helm-tags + :persistent-help "Go to line" + :persistent-action (lambda (candidate) + (helm-etags-action-goto 'find-file candidate) + (helm-highlight-current-line)))) + +(defcustom helm-etags-fuzzy-match nil + "Use fuzzy matching in `helm-etags-select'." + :group 'helm-tags + :type 'boolean + :set (lambda (var val) + (set var val) + (setq helm-source-etags-select + (helm-etags-build-source)))) + +(defvar find-tag-marker-ring) + +(defsubst helm-etags--file-from-tag (fname) + (cl-loop for ext in + (cons "" (remove "" tags-compression-info-list)) + for file = (concat fname ext) + when (file-exists-p file) + return file)) + +(defun helm-etags-action-goto (switcher candidate) + "Helm default action to jump to an etags entry in other window." + (require 'etags) + (deactivate-mark t) + (helm-log-run-hook 'helm-goto-line-before-hook) + (let* ((split (helm-grep-split-line candidate)) + (fname (cl-loop for tagf being the hash-keys of helm-etags-cache + for f = (expand-file-name + (car split) (file-name-directory tagf)) + ;; Try to find an existing file, possibly compressed. + when (helm-etags--file-from-tag f) + return it)) + (elm (cl-caddr split)) + (linum (string-to-number (cadr split)))) + (if (null fname) + (error "file %s not found" fname) + (ring-insert find-tag-marker-ring (point-marker)) + (funcall switcher fname) + (helm-goto-line linum t) + (when (search-forward elm nil t) + (goto-char (match-beginning 0)))))) + +(defun helm-etags-mtime (file) + "Last modification time of etags tag FILE." + (cadr (nth 5 (file-attributes file)))) + +(defun helm-etags-file-modified-p (file) + "Check if tag FILE have been modified in this session. +If FILE is nil return nil." + (let ((last-modif (and file + (assoc-default file helm-etags-mtime-alist)))) + (and last-modif + (/= last-modif (helm-etags-mtime file))))) + +;;;###autoload +(defun helm-etags-select (reinit) + "Preconfigured helm for etags. +If called with a prefix argument REINIT +or if any of the tag files have been modified, reinitialize cache. + +This function aggregates three sources of tag files: + + 1) An automatically located file in the parent directories, + by `helm-etags-get-tag-file'. + 2) `tags-file-name', which is commonly set by `find-tag' command. + 3) `tags-table-list' which is commonly set by `visit-tags-table' command." + (interactive "P") + (let ((tag-files (helm-etags-all-tag-files)) + (helm-execute-action-at-once-if-one + helm-etags-execute-action-at-once-if-one) + (str (if (region-active-p) + (buffer-substring-no-properties + (region-beginning) (region-end)) + (thing-at-point 'symbol)))) + (if (cl-notany 'file-exists-p tag-files) + (message "Error: No tag file found.\ +Create with etags shell command, or visit with `find-tag' or `visit-tags-table'.") + (cl-loop for k being the hash-keys of helm-etags-cache + unless (member k tag-files) + do (remhash k helm-etags-cache)) + (mapc (lambda (f) + (when (or (equal reinit '(4)) + (and helm-etags-mtime-alist + (helm-etags-file-modified-p f))) + (remhash f helm-etags-cache))) + tag-files) + (unless helm-source-etags-select + (setq helm-source-etags-select + (helm-etags-build-source))) + (helm :sources 'helm-source-etags-select + :keymap helm-etags-map + :default (and (stringp str) + (if (or helm-etags-fuzzy-match + (and (eq major-mode 'haskell-mode) + (string-match "[']\\'" str))) + str + (list (concat "\\_<" str "\\_>") str))) + :buffer "*helm etags*")))) + +(provide 'helm-tags) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-tags.el ends here diff --git a/elpa/helm-20191031.839/helm-types.el b/elpa/helm-20191031.839/helm-types.el new file mode 100644 index 00000000..868e7974 --- /dev/null +++ b/elpa/helm-20191031.839/helm-types.el @@ -0,0 +1,322 @@ +;;; helm-types.el --- Helm types classes and methods. -*- lexical-binding: t -*- + +;; Copyright (C) 2015 ~ 2019 Thierry Volpiatto + +;; Author: Thierry Volpiatto +;; URL: http://github.com/emacs-helm/helm + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + + +;;; Code: + +(require 'cl-lib) +(require 'eieio) + + +;; Files +(defclass helm-type-file (helm-source) () + "A class to define helm type file.") + +(defmethod helm-source-get-action-from-type ((object helm-type-file)) + (slot-value object 'action)) + +(defun helm-actions-from-type-file () + (let ((source (make-instance 'helm-type-file))) + (helm--setup-source source) + (helm-source-get-action-from-type source))) + +(defvar helm-generic-files-map + (let ((map (make-sparse-keymap))) + (set-keymap-parent map helm-map) + (define-key map (kbd "C-]") 'helm-ff-run-toggle-basename) + (define-key map (kbd "C-s") 'helm-ff-run-grep) + (define-key map (kbd "M-g s") 'helm-ff-run-grep) + (define-key map (kbd "M-g z") 'helm-ff-run-zgrep) + (define-key map (kbd "M-g p") 'helm-ff-run-pdfgrep) + (define-key map (kbd "C-c g") 'helm-ff-run-gid) + (define-key map (kbd "M-R") 'helm-ff-run-rename-file) + (define-key map (kbd "M-C") 'helm-ff-run-copy-file) + (define-key map (kbd "M-B") 'helm-ff-run-byte-compile-file) + (define-key map (kbd "M-L") 'helm-ff-run-load-file) + (define-key map (kbd "M-S") 'helm-ff-run-symlink-file) + (define-key map (kbd "M-H") 'helm-ff-run-hardlink-file) + (define-key map (kbd "M-D") 'helm-ff-run-delete-file) + (define-key map (kbd "C-=") 'helm-ff-run-ediff-file) + (define-key map (kbd "C-c =") 'helm-ff-run-ediff-merge-file) + (define-key map (kbd "C-c o") 'helm-ff-run-switch-other-window) + (define-key map (kbd "C-c r") 'helm-ff-run-find-file-as-root) + (define-key map (kbd "C-c C-o") 'helm-ff-run-switch-other-frame) + (define-key map (kbd "M-i") 'helm-ff-properties-persistent) + (define-key map (kbd "C-c C-x") 'helm-ff-run-open-file-externally) + (define-key map (kbd "C-c X") 'helm-ff-run-open-file-with-default-tool) + (define-key map (kbd "M-.") 'helm-ff-run-etags) + (define-key map (kbd "C-c @") 'helm-ff-run-insert-org-link) + (define-key map (kbd "C-x C-q") 'helm-ff-run-marked-files-in-dired) + (define-key map (kbd "C-c C-a") 'helm-ff-run-mail-attach-files) + map) + "Generic Keymap for files.") + +(defcustom helm-type-file-actions + (helm-make-actions + "Find file" 'helm-find-many-files + "Find file as root" 'helm-find-file-as-root + "Find file other window" 'helm-find-files-other-window + "Find file other frame" 'find-file-other-frame + "Open dired in file's directory" 'helm-open-dired + "Attach file(s) to mail buffer `C-c C-a'" 'helm-ff-mail-attach-files + "Marked files in dired" 'helm-marked-files-in-dired + "Grep File(s) `C-u recurse'" 'helm-find-files-grep + "Zgrep File(s) `C-u Recurse'" 'helm-ff-zgrep + "Pdfgrep File(s)" 'helm-ff-pdfgrep + "Insert as org link" 'helm-files-insert-as-org-link + "Checksum File" 'helm-ff-checksum + "Ediff File" 'helm-find-files-ediff-files + "Ediff Merge File" 'helm-find-files-ediff-merge-files + "Etags `M-., C-u reload tag file'" 'helm-ff-etags-select + "View file" 'view-file + "Insert file" 'insert-file + "Add marked files to file-cache" 'helm-ff-cache-add-file + "Delete file(s)" 'helm-ff-delete-files + "Copy file(s) `M-C, C-u to follow'" 'helm-find-files-copy + "Rename file(s) `M-R, C-u to follow'" 'helm-find-files-rename + "Symlink files(s) `M-S, C-u to follow'" 'helm-find-files-symlink + "Relsymlink file(s) `C-u to follow'" 'helm-find-files-relsymlink + "Hardlink file(s) `M-H, C-u to follow'" 'helm-find-files-hardlink + "Open file externally (C-u to choose)" 'helm-open-file-externally + "Open file with default tool" 'helm-open-file-with-default-tool + "Find file in hex dump" 'hexl-find-file) + "Default actions for type files." + :group 'helm-files + :type '(alist :key-type string :value-type function)) + +(defmethod helm--setup-source :primary ((_source helm-type-file))) + +(defmethod helm--setup-source :before ((source helm-type-file)) + (setf (slot-value source 'action) 'helm-type-file-actions) + (setf (slot-value source 'persistent-help) "Show this file") + (setf (slot-value source 'action-transformer) + '(helm-transform-file-load-el + helm-transform-file-browse-url + helm-transform-file-cache)) + (setf (slot-value source 'candidate-transformer) + '(helm-skip-boring-files + helm-w32-pathname-transformer)) + (setf (slot-value source 'filtered-candidate-transformer) + 'helm-highlight-files) + (setf (slot-value source 'help-message) 'helm-generic-file-help-message) + (setf (slot-value source 'mode-line) (list "File(s)" helm-mode-line-string)) + (setf (slot-value source 'keymap) helm-generic-files-map) + (setf (slot-value source 'group) 'helm-files)) + + +;; Bookmarks +(defclass helm-type-bookmark (helm-source) () + "A class to define type bookmarks.") + +(defcustom helm-type-bookmark-actions + (helm-make-actions + "Jump to bookmark" 'helm-bookmark-jump + "Jump to BM other window" 'helm-bookmark-jump-other-window + "Jump to BM other frame" 'helm-bookmark-jump-other-frame + "Bookmark edit annotation" 'bookmark-edit-annotation + "Bookmark show annotation" 'bookmark-show-annotation + "Delete bookmark(s)" 'helm-delete-marked-bookmarks + "Edit Bookmark" 'helm-bookmark-edit-bookmark + "Rename bookmark" 'helm-bookmark-rename + "Relocate bookmark" 'bookmark-relocate) + "Default actions for type bookmarks." + :group 'helm-bookmark + :type '(alist :key-type string + :value-type function)) + +(defmethod helm-source-get-action-from-type ((object helm-type-bookmark)) + (slot-value object 'action)) + +(defmethod helm--setup-source :primary ((_source helm-type-bookmark))) + +(defmethod helm--setup-source :before ((source helm-type-bookmark)) + (setf (slot-value source 'action) 'helm-type-bookmark-actions) + (setf (slot-value source 'keymap) helm-bookmark-map) + (setf (slot-value source 'mode-line) (list "Bookmark(s)" helm-mode-line-string)) + (setf (slot-value source 'help-message) 'helm-bookmark-help-message) + (setf (slot-value source 'migemo) t) + (setf (slot-value source 'follow) 'never) + (setf (slot-value source 'group) 'helm-bookmark)) + + +;; Buffers +(defclass helm-type-buffer (helm-source) () + "A class to define type buffer.") + +(defcustom helm-type-buffer-actions + (helm-make-actions + "Switch to buffer(s)" 'helm-buffer-switch-buffers + "Switch to buffer(s) other window `C-c o'" + 'helm-buffer-switch-buffers-other-window + "Switch to buffer other frame `C-c C-o'" + 'switch-to-buffer-other-frame + (lambda () (and (fboundp 'tab-bar-mode) + "Switch to buffer other tab `C-c C-t'")) + 'switch-to-buffer-other-tab + "Browse project `C-x C-d'" + 'helm-buffers-browse-project + "Query replace regexp `C-M-%'" + 'helm-buffer-query-replace-regexp + "Query replace `M-%'" 'helm-buffer-query-replace + "View buffer" 'view-buffer + "Display buffer" 'display-buffer + "Rename buffer `M-R'" 'helm-buffers-rename-buffer + "Grep buffer(s) `M-g s' (C-u grep all buffers)" + 'helm-zgrep-buffers + "Multi occur buffer(s) `C-s (C-u search also in current)'" + 'helm-multi-occur-as-action + "Revert buffer(s) `M-G'" 'helm-revert-marked-buffers + "Insert buffer" 'insert-buffer + "Kill buffer(s) `M-D'" 'helm-kill-marked-buffers + "Diff with file `C-='" 'diff-buffer-with-file + "Ediff Marked buffers `C-c ='" 'helm-ediff-marked-buffers + "Ediff Merge marked buffers `M-='" + (lambda (candidate) + (helm-ediff-marked-buffers candidate t))) + "Default actions for type buffers." + :group 'helm-buffers + :type '(alist :key-type string :value-type function)) + +(defmethod helm-source-get-action-from-type ((object helm-type-buffer)) + (slot-value object 'action)) + +(defmethod helm--setup-source :primary ((_source helm-type-buffer))) + +(defmethod helm--setup-source :before ((source helm-type-buffer)) + (setf (slot-value source 'action) 'helm-type-buffer-actions) + (setf (slot-value source 'persistent-help) "Show this buffer") + (setf (slot-value source 'mode-line) (list "Buffer(s)" helm-mode-line-string)) + (setf (slot-value source 'filtered-candidate-transformer) + '(helm-skip-boring-buffers + helm-buffers-sort-transformer + helm-highlight-buffers)) + (setf (slot-value source 'group) 'helm-buffers)) + +;; Functions +(defclass helm-type-function (helm-source) () + "A class to define helm type function.") + +(defcustom helm-type-function-actions + (helm-make-actions + "Describe command" 'describe-function + "Add command to kill ring" 'helm-kill-new + "Go to command's definition" 'find-function + "Debug on entry" 'debug-on-entry + "Cancel debug on entry" 'cancel-debug-on-entry + "Trace function" 'trace-function + "Trace function (background)" 'trace-function-background + "Untrace function" 'untrace-function) + "Default actions for type functions." + :group 'helm-elisp + :type '(alist :key-type string :value-type function)) + +(defmethod helm-source-get-action-from-type ((object helm-type-function)) + (slot-value object 'action)) + +(defun helm-actions-from-type-function () + (let ((source (make-instance 'helm-type-function))) + (helm--setup-source source) + (helm-source-get-action-from-type source))) + +(defmethod helm--setup-source :primary ((_source helm-type-function))) + +(defmethod helm--setup-source :before ((source helm-type-function)) + (setf (slot-value source 'action) 'helm-type-function-actions) + (setf (slot-value source 'action-transformer) + 'helm-transform-function-call-interactively) + (setf (slot-value source 'candidate-transformer) + 'helm-mark-interactive-functions) + (setf (slot-value source 'coerce) 'helm-symbolify)) + + +;; Commands +(defclass helm-type-command (helm-source) () + "A class to define helm type command.") + +(defun helm-actions-from-type-command () + (let ((source (make-instance 'helm-type-command))) + (helm--setup-source source) + (helm-source-get-action-from-type source))) + +(defcustom helm-type-command-actions + (append (helm-make-actions + "Call interactively" 'helm-call-interactively) + (helm-actions-from-type-function)) + "Default actions for type command." + :group 'helm-command + :type '(alist :key-type string :value-type function)) + +(defmethod helm--setup-source :primary ((_source helm-type-command))) + +(defmethod helm--setup-source :before ((source helm-type-command)) + (setf (slot-value source 'action) 'helm-type-command-actions) + (setf (slot-value source 'coerce) 'helm-symbolify) + (setf (slot-value source 'persistent-action) 'describe-function) + (setf (slot-value source 'group) 'helm-command)) + +;; Timers +(defclass helm-type-timers (helm-source) () + "A class to define helm type timers.") + +(defcustom helm-type-timers-actions + '(("Cancel Timer" . (lambda (_timer) + (let ((mkd (helm-marked-candidates))) + (cl-loop for timer in mkd + do (cancel-timer timer))))) + ("Describe Function" . (lambda (tm) + (describe-function (timer--function tm)))) + ("Find Function" . (lambda (tm) + (helm-aif (timer--function tm) + (if (byte-code-function-p it) + (message "Can't find anonymous function `%s'" it) + (find-function it)))))) + "Default actions for type timers." + :group 'helm-elisp + :type '(alist :key-type string :value-type function)) + +(defmethod helm--setup-source :primary ((_source helm-type-timers))) + +(defmethod helm--setup-source :before ((source helm-type-timers)) + (setf (slot-value source 'action) 'helm-type-timers-actions) + (setf (slot-value source 'persistent-action) + (lambda (tm) + (describe-function (timer--function tm)))) + (setf (slot-value source 'persistent-help) "Describe Function") + (setf (slot-value source 'group) 'helm-elisp)) + +;; Builders. +(defun helm-build-type-file () + (helm-make-type 'helm-type-file)) + +(defun helm-build-type-function () + (helm-make-type 'helm-type-function)) + +(defun helm-build-type-command () + (helm-make-type 'helm-type-command)) + +(provide 'helm-types) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-types.el ends here diff --git a/elpa/helm-20191031.839/helm-utils.el b/elpa/helm-20191031.839/helm-utils.el new file mode 100644 index 00000000..f246dd51 --- /dev/null +++ b/elpa/helm-20191031.839/helm-utils.el @@ -0,0 +1,1069 @@ +;;; helm-utils.el --- Utilities Functions for helm. -*- lexical-binding: t -*- + +;; Copyright (C) 2012 ~ 2019 Thierry Volpiatto + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'cl-lib) +(require 'helm) +(require 'helm-help) +(eval-when-compile (require 'dired)) + +(declare-function helm-find-files-1 "helm-files.el" (fname &optional preselect)) +(declare-function popup-tip "ext:popup") +(declare-function markdown-show-subtree "outline.el") +(declare-function outline-show-subtree "outline.el") +(declare-function org-reveal "org.el") +(declare-function tab-bar-tabs "tab-bar.el") +(declare-function tab-bar-select-tab "tab-bar.el") +(defvar org-directory) +(defvar winner-boring-buffers) +(defvar helm-show-completion-overlay) + + +(defgroup helm-utils nil + "Utilities routines for Helm." + :group 'helm) + +(defcustom helm-su-or-sudo "sudo" + "What command to use for root access." + :type 'string + :group 'helm-utils) + +(defcustom helm-default-kbsize 1024.0 + "Default Kbsize to use for showing files size. +It is a float, usually 1024.0 but could be 1000.0 on some systems." + :group 'helm-utils + :type 'float) + +(define-obsolete-variable-alias + 'helm-highlight-number-lines-around-point + 'helm-highlight-matches-around-point-max-lines + "20160119") + +(defcustom helm-highlight-matches-around-point-max-lines 15 + "Number of lines around point where matched items are highlighted." + :group 'helm-utils + :type 'integer) + +(defcustom helm-buffers-to-resize-on-pa nil + "A list of helm buffers where the helm-window should be reduced on persistent actions." + :group 'helm-utils + :type '(repeat (choice string))) + +(defcustom helm-resize-on-pa-text-height 12 + "The size of the helm-window when resizing on persistent action." + :group 'helm-utils + :type 'integer) + +(defcustom helm-sources-using-help-echo-popup '("Moccur" "Imenu in all buffers" + "Ack-Grep" "AG" "RG" "Gid" "Git-Grep") + "Show the buffer name or the filename in a popup at selection." + :group 'helm-utils + :type '(repeat (choice string))) + +(defcustom helm-html-decode-entities-function #'helm-html-decode-entities-string + "Function used to decode html entities in html bookmarks. +Helm comes by default with `helm-html-decode-entities-string', if you need something +more sophisticated you can use `w3m-decode-entities-string' if available. + +In emacs itself org-entities seems broken and `xml-substitute-numeric-entities' +supports only numeric entities." + :group 'helm-utils + :type 'function) + + +(defvar helm-goto-line-before-hook '(helm-save-current-pos-to-mark-ring) + "Run before jumping to line. +This hook run when jumping from `helm-goto-line', `helm-etags-default-action', +and `helm-imenu-default-action'. +This allow you to retrieve a previous position after using the different helm +tools for searching (etags, grep, gid, (m)occur etc...). +By default positions are added to `mark-ring' you can also add to register +by using instead (or adding) `helm-save-pos-to-register-before-jump'. +In this case last position is added to the register +`helm-save-pos-before-jump-register'.") + +(defvar helm-save-pos-before-jump-register ?_ + "The register where `helm-save-pos-to-register-before-jump' save position.") + +(defconst helm-html-entities-alist + '((""" . 34) ;; " + (">" . 62) ;; > + ("<" . 60) ;; < + ("&" . 38) ;; & + ("€" . 8364) ;; € + ("Ÿ" . 89) ;; Y + ("¡" . 161) ;; ¡ + ("¢" . 162) ;; ¢ + ("£" . 163) ;; £ + ("¤" . 164) ;; ¤ + ("¥" . 165) ;; Â¥ + ("¦" . 166) ;; ¦ + ("§" . 167) ;; § + ("¨" . 32) ;; SPC + ("©" . 169) ;; © + ("ª" . 97) ;; a + ("«" . 171) ;; « + ("¬" . 172) ;; ¬ + ("&masr;" . 174) ;; ® + ("°" . 176) ;; ° + ("±" . 177) ;; ± + ("²" . 50) ;; 2 + ("³" . 51) ;; 3 + ("´" . 39) ;; ' + ("µ" . 956) ;; μ + ("¶" . 182) ;; ¶ + ("·" . 183) ;; · + ("¸" . 32) ;; SPC + ("¹" . 49) ;; 1 + ("º" . 111) ;; o + ("»" . 187) ;; » + ("¼" . 49) ;; 1 + ("½" . 49) ;; 1 + ("¾" . 51) ;; 3 + ("¿" . 191) ;; ¿ + ("À" . 192) ;; À + ("Á" . 193) ;; Á + ("Â" . 194) ;;  + ("Ã" . 195) ;; à + ("Ä" . 196) ;; Ä + ("Å" . 197) ;; Å + ("&Aelig" . 198) ;; Æ + ("Ç" . 199) ;; Ç + ("È" . 200) ;; È + ("É" . 201) ;; É + ("Ê" . 202) ;; Ê + ("Ë" . 203) ;; Ë + ("Ì" . 204) ;; Ì + ("Í" . 205) ;; Í + ("Î" . 206) ;; Î + ("Ï" . 207) ;; Ï + ("ð" . 208) ;; Ð + ("Ñ" . 209) ;; Ñ + ("Ò" . 210) ;; Ò + ("Ó" . 211) ;; Ó + ("Ô" . 212) ;; Ô + ("Õ" . 213) ;; Õ + ("Ö" . 214) ;; Ö + ("×" . 215) ;; × + ("Ø" . 216) ;; Ø + ("Ù" . 217) ;; Ù + ("Ú" . 218) ;; Ú + ("Û" . 219) ;; Û + ("Ü" . 220) ;; Ü + ("Ý" . 221) ;; Ý + ("þ" . 222) ;; Þ + ("ß" . 223) ;; ß + ("à" . 224) ;; à + ("á" . 225) ;; á + ("â" . 226) ;; â + ("ã" . 227) ;; ã + ("ä" . 228) ;; ä + ("å" . 229) ;; Ã¥ + ("æ" . 230) ;; æ + ("ç" . 231) ;; ç + ("è" . 232) ;; è + ("é" . 233) ;; é + ("ê" . 234) ;; ê + ("ë" . 235) ;; ë + ("ì" . 236) ;; ì + ("í" . 237) ;; í + ("î" . 238) ;; î + ("ï" . 239) ;; ï + ("ð" . 240) ;; ð + ("ñ" . 241) ;; ñ + ("ò" . 242) ;; ò + ("ó" . 243) ;; ó + ("ô" . 244) ;; ô + ("õ" . 245) ;; õ + ("ö" . 246) ;; ö + ("÷" . 247) ;; ÷ + ("ø" . 248) ;; ø + ("ù" . 249) ;; ù + ("ú" . 250) ;; ú + ("û" . 251) ;; û + ("ü" . 252) ;; ü + ("ý" . 253) ;; ý + ("þ" . 254) ;; þ + ("ÿ" . 255) ;; ÿ + ("®" . 174) ;; ® + ("­" . 173)) ;; ­ + + "Table of html character entities and values.") + +(defvar helm-find-many-files-after-hook nil + "Hook that run at end of `helm-find-many-files'.") + +;;; Faces. +;; +(defface helm-selection-line + '((t (:inherit highlight :distant-foreground "black"))) + "Face used in the `helm-current-buffer' when jumping to candidate." + :group 'helm-faces) + +(defface helm-match-item + '((t (:inherit isearch))) + "Face used to highlight item matched in a selected line." + :group 'helm-faces) + + +;;; Utils functions +;; +;; +(defcustom helm-window-prefer-horizontal-split nil + "Maybe switch to other window vertically when non nil. + +Possible values are t, nil and `decide'. + +When t switch vertically. +When nil switch horizontally. +When `decide' try to guess if it is possible to switch vertically +according to the setting of `split-width-threshold' and the size of +the window from where splitting is done. + +Note that when using `decide' and `split-width-threshold' is nil, the +behavior is the same that with a nil value." + :group 'helm-utils + :type '(choice + (const :tag "Split window vertically" t) + (const :tag "Split window horizontally" nil) + (symbol :tag "Guess how to split window" 'decide))) + +(defcustom helm-window-show-buffers-function #'helm-window-default-split-fn + "The default function to use when opening several buffers at once. +It is typically used to rearrange windows." + :group 'helm-utils + :type '(choice + (function :tag "Split windows vertically or horizontally" + helm-window-default-split-fn) + (function :tag "Split in alternate windows" + helm-window-alternate-split-fn) + (function :tag "Split windows in mosaic" + helm-window-mosaic-fn))) + +(defun helm-window-show-buffers (buffers &optional other-window) + "Show BUFFERS. + +If more than one buffer marked switch to these buffers in separate windows. +If OTHER-WINDOW is non-nil, keep current buffer and switch to others buffers +in separate windows. +If a prefix arg is given split windows vertically." + (let ((initial-ow-fn (if (cdr (window-list)) + #'switch-to-buffer-other-window + #'helm-window-other-window))) + (if (cdr buffers) + (funcall helm-window-show-buffers-function buffers + (and other-window initial-ow-fn)) + (if other-window + (funcall initial-ow-fn (car buffers)) + (helm-buffers-switch-to-buffer-or-tab (car buffers)))))) + +(defun helm-buffers-switch-to-buffer-or-tab (buffer) + "Switch to BUFFER in its tab if some." + (if (and (fboundp 'tab-bar-mode) + helm-buffers-maybe-switch-to-tab) + (let* ((tabs (tab-bar-tabs)) + (tab-names (mapcar (lambda (tab) + (cdr (assq 'name tab))) + (tab-bar-tabs))) + (bname (buffer-name (get-buffer buffer))) + (tab (helm-buffers--get-tab-from-name bname tabs))) + (if (helm-buffers--buffer-in-tab-p bname tab-names) + (progn + (tab-bar-select-tab tab) + (select-window (get-buffer-window bname))) + (switch-to-buffer buffer))) + (switch-to-buffer buffer))) + +(defun helm-buffers--get-tab-from-name (tab-name tabs) + "Return tab from TABS when it contains TAB-NAME." + (cl-loop for tab in tabs + when (member tab-name (split-string (cdr (assq 'name tab)) ", " t)) + return tab)) + +(defun helm-buffers--buffer-in-tab-p (buffer-name tab-names) + "Check if BUFFER-NAME is in TAB-NAMES list." + (cl-loop for name in tab-names + ;; Buf names are separated with "," in TAB-NAMES + ;; e.g. '("tab-bar.el" "*scratch*, helm-buffers.el"). + thereis (member buffer-name (split-string name ", " t)))) + +(defun helm-window-default-split-fn (candidates &optional other-window-fn) + "Split windows in one direction and balance them. + +Direction can be controlled via `helm-window-prefer-horizontal-split'. +If a prefix arg is given split windows the other direction. +This function is suitable for `helm-window-show-buffers-function'." + (if other-window-fn + (funcall other-window-fn (car candidates)) + (switch-to-buffer (car candidates))) + (save-selected-window + (cl-loop with nosplit + for b in (cdr candidates) + when nosplit return + (message "Too many buffers to visit simultaneously") + do (condition-case _err + (helm-window-other-window b 'balance) + (error (setq nosplit t) nil))))) + +(defun helm-window-alternate-split-fn (candidates &optional other-window-fn) + "Split windows horizontally and vertically in alternate fashion. + +Direction can be controlled via `helm-window-prefer-horizontal-split'. +If a prefix arg is given split windows the other direction. +This function is suitable for `helm-window-show-buffers-function'." + (if other-window-fn + (funcall other-window-fn (car candidates)) + (switch-to-buffer (car candidates))) + (let (right-side) + (save-selected-window + (cl-loop with nosplit + for b in (cdr candidates) + when nosplit return + (message "Too many buffers to visit simultaneously") + do (condition-case _err + (let ((helm-current-prefix-arg right-side)) + (helm-window-other-window b) + (setq right-side (not right-side))) + (error (setq nosplit t) nil)))))) + +(defun helm-window-mosaic-fn (candidates &optional other-window-fn) + "Make an as-square-as-possible window mosaic of the CANDIDATES buffers. + +If rectangular, the long side is in the direction given by +`helm-window-prefer-horizontal-split': if non-nil, it is horizontal, vertical +otherwise. +If OTHER-WINDOW-FN is non-nil, current windows are included in the mosaic. +This function is suitable for `helm-window-show-buffers-function'." + (when other-window-fn + (setq candidates (append (mapcar 'window-buffer (window-list)) candidates))) + (delete-other-windows) + (let* ((helm-window-prefer-horizontal-split + (if (eq helm-window-prefer-horizontal-split 'decide) + (and (numberp split-width-threshold) + (>= (window-width (selected-window)) + split-width-threshold)) + helm-window-prefer-horizontal-split)) + mosaic-length-tile-count + mosaic-width-tile-count + mosaic-length-tile-size + mosaic-width-tile-size + next-window) + ;; If 4 tiles, make 2x2 mosaic. + ;; If 5-6 tiles, make 2x3 mosaic with direction depending on `helm-window-prefer-horizontal-split'. + ;; If 7-9 tiles, make 3x3 mosaic. And so on. + (setq mosaic-length-tile-count (ceiling (sqrt (length candidates)))) + (setq mosaic-width-tile-count + (if (<= (length candidates) (* mosaic-length-tile-count (1- mosaic-length-tile-count))) + (1- mosaic-length-tile-count) + mosaic-length-tile-count)) + ;; We lower-bound the tile size, otherwise the function would + ;; fail during the first inner split. + ;; There is consequently no need to check for errors when + ;; splitting. + (let ((frame-mosaic-length-direction-size (frame-height)) + (frame-mosaic-width-direction-size (frame-width)) + (window-mosaic-length-direction-min-size window-min-height) + (window-mosaic-width-direction-min-size window-min-width)) + (if helm-window-prefer-horizontal-split + (setq frame-mosaic-length-direction-size (frame-width) + frame-mosaic-width-direction-size (frame-height) + window-mosaic-length-direction-min-size window-min-width + window-mosaic-width-direction-min-size window-min-height)) + (setq mosaic-length-tile-size (max + (/ frame-mosaic-length-direction-size mosaic-length-tile-count) + window-mosaic-length-direction-min-size) + mosaic-width-tile-size (max + (/ frame-mosaic-width-direction-size mosaic-width-tile-count) + window-mosaic-width-direction-min-size)) + ;; Shorten `candidates' to `max-tiles' elements. + (let ((max-tiles (* (/ frame-mosaic-length-direction-size mosaic-length-tile-size) + (/ frame-mosaic-width-direction-size mosaic-width-tile-size)))) + (when (> (length candidates) max-tiles) + (message "Too many buffers to visit simultaneously") + (setcdr (nthcdr (- max-tiles 1) candidates) nil)))) + ;; Make the mosaic. + (while candidates + (when (> (length candidates) mosaic-length-tile-count) + (setq next-window (split-window nil + mosaic-width-tile-size + (not helm-window-prefer-horizontal-split)))) + (switch-to-buffer (pop candidates)) + (dotimes (_ (min (1- mosaic-length-tile-count) (length candidates))) + (select-window (split-window nil + mosaic-length-tile-size + helm-window-prefer-horizontal-split)) + (switch-to-buffer (pop candidates))) + (when next-window + (select-window next-window))))) + +(defun helm-window-other-window (buffer-or-name &optional balance) + "Switch to BUFFER-OR-NAME in other window. +Direction can be controlled via `helm-window-prefer-horizontal-split'. +If a prefix arg is given split windows the other direction. +When argument BALANCE is provided `balance-windows'." + (let* ((helm-window-prefer-horizontal-split + (if (eq helm-window-prefer-horizontal-split 'decide) + (and (numberp split-width-threshold) + (>= (window-width (selected-window)) + split-width-threshold)) + helm-window-prefer-horizontal-split)) + (right-side (if helm-window-prefer-horizontal-split + (not helm-current-prefix-arg) + helm-current-prefix-arg))) + (select-window (split-window nil nil right-side)) + (and balance (balance-windows)) + (switch-to-buffer buffer-or-name))) + +(cl-defun helm-current-buffer-narrowed-p (&optional + (buffer helm-current-buffer)) + "Check if BUFFER is narrowed. +Default is `helm-current-buffer'." + (with-current-buffer buffer + (let ((beg (point-min)) + (end (point-max)) + (total (buffer-size))) + (or (/= beg 1) (/= end (1+ total)))))) + +(defun helm-goto-char (loc) + "Go to char, revealing if necessary." + (goto-char loc) + (let ((fn (cond ((eq major-mode 'org-mode) + ;; On some old Emacs versions org may not be loaded. + (require 'org) + #'org-reveal) + ((and (boundp 'outline-minor-mode) + outline-minor-mode) + #'outline-show-subtree) + ((and (boundp 'markdown-mode-map) + (derived-mode-p 'markdown-mode)) + #'markdown-show-subtree)))) + ;; outline may fail in some conditions e.g. with markdown enabled + ;; (issue #1919). + (condition-case nil + (and fn (funcall fn)) + (error nil)))) + +(defun helm-goto-line (lineno &optional noanim) + "Goto LINENO opening only outline headline if needed. +Animation is used unless NOANIM is non--nil." + (helm-log-run-hook 'helm-goto-line-before-hook) + (helm-match-line-cleanup) + (unless helm-alive-p + (with-helm-current-buffer + (unless helm-yank-point (setq helm-yank-point (point))))) + (goto-char (point-min)) + (helm-goto-char (point-at-bol lineno)) + (unless noanim + (helm-highlight-current-line))) + +(defun helm-save-pos-to-register-before-jump () + "Save current buffer position to `helm-save-pos-before-jump-register'. +To use this add it to `helm-goto-line-before-hook'." + (with-helm-current-buffer + (unless helm-in-persistent-action + (point-to-register helm-save-pos-before-jump-register)))) + +(defun helm-save-current-pos-to-mark-ring () + "Save current buffer position to mark ring. +To use this add it to `helm-goto-line-before-hook'." + (with-helm-current-buffer + (unless helm-in-persistent-action + (set-marker (mark-marker) (point)) + (push-mark (point) 'nomsg)))) + +(defun helm-show-all-candidates-in-source (arg) + "Toggle all or only candidate-number-limit cands in current source. +With a numeric prefix arg show only the ARG number of candidates. +The prefix arg have no effect when toggling to only +candidate-number-limit." + (interactive "p") + (with-helm-alive-p + (with-helm-buffer + (if helm-source-filter + (progn + (setq-local helm-candidate-number-limit + (default-value 'helm-candidate-number-limit)) + (helm-set-source-filter nil)) + (with-helm-default-directory (helm-default-directory) + (setq-local helm-candidate-number-limit (and (> arg 1) arg)) + (helm-set-source-filter + (list (helm-get-current-source)))))))) +(put 'helm-show-all-candidates-in-source 'helm-only t) + +(defun helm-display-all-sources () + "Display all sources previously hidden by `helm-set-source-filter'." + (interactive) + (with-helm-alive-p + (helm-set-source-filter nil))) +(put 'helm-display-all-sources 'helm-only t) + +(defun helm-displaying-source-names () + "Return the list of sources name for this helm session." + (with-current-buffer helm-buffer + (goto-char (point-min)) + (cl-loop with pos + while (setq pos (next-single-property-change (point) 'helm-header)) + do (goto-char pos) + collect (buffer-substring-no-properties (point-at-bol)(point-at-eol)) + do (forward-line 1)))) + +(defun helm-handle-winner-boring-buffers () + "Add `helm-buffer' to `winner-boring-buffers' when quitting/exiting helm. +Add this function to `helm-cleanup-hook' when you don't want to see helm buffers +after running winner-undo/redo." + (require 'winner) + (cl-pushnew helm-buffer winner-boring-buffers :test 'equal)) +(add-hook 'helm-cleanup-hook #'helm-handle-winner-boring-buffers) + +(defun helm-quit-and-find-file () + "Drop into `helm-find-files' from `helm'. +If current selection is a buffer or a file, `helm-find-files' +from its directory." + (interactive) + (with-helm-alive-p + (require 'helm-grep) + (require 'helm-elisp) + (helm-run-after-exit + (lambda (f) + ;; Ensure specifics `helm-execute-action-at-once-if-one' + ;; fns don't run here. + (let (helm-execute-action-at-once-if-one + helm-actions-inherit-frame-settings) ; use this-command + (if (file-exists-p f) + (helm-find-files-1 (file-name-directory f) + (concat + "^" + (regexp-quote + (if helm-ff-transformer-show-only-basename + (helm-basename f) f)))) + (helm-find-files-1 f)))) + (let* ((sel (helm-get-selection)) + (marker (and (consp sel) (markerp (cdr sel)))) + (grep-line (and (stringp sel) + (helm-grep-split-line sel))) + (occur-fname (helm-aand (numberp sel) + (helm-attr 'buffer-name) + (buffer-file-name (get-buffer it)))) + (bmk-name (and (stringp sel) + (not grep-line) + (replace-regexp-in-string "\\`\\*" "" sel))) + (bmk (and bmk-name (assoc bmk-name bookmark-alist))) + (buf (helm-aif (and (bufferp sel) (get-buffer sel)) + (buffer-name it))) + (pkg (and (stringp sel) + (get-text-property 0 'tabulated-list-id sel))) + (default-preselection (or (buffer-file-name helm-current-buffer) + default-directory))) + (cond + ;; Buffer. + (buf (or (buffer-file-name sel) + (car (rassoc buf dired-buffers)) + (and (with-current-buffer buf + (eq major-mode 'org-agenda-mode)) + org-directory + (expand-file-name org-directory)) + (with-current-buffer buf + (expand-file-name default-directory)))) + ;; imenu (marker). + (marker + (or (buffer-file-name (marker-buffer (cdr sel))) + default-preselection)) + ;; Bookmark. + (bmk (helm-aif (bookmark-get-filename bmk) + (if (and helm--url-regexp + (string-match helm--url-regexp it)) + it (expand-file-name it)) + (expand-file-name default-directory))) + ((and (stringp sel) (or (file-remote-p sel) + (file-exists-p sel))) + (expand-file-name sel)) + ;; Grep. + ((and grep-line (file-exists-p (car grep-line))) + (expand-file-name (car grep-line))) + ;; Occur. + ((and occur-fname (file-exists-p occur-fname)) + (expand-file-name occur-fname)) + ;; Package (installed). + ((and pkg (package-installed-p pkg)) + (expand-file-name (package-desc-dir pkg))) + ;; Url. + ((and (stringp sel) helm--url-regexp (string-match helm--url-regexp sel)) sel) + ;; Exit brutally from a `with-helm-show-completion' + ((and helm-show-completion-overlay + (overlayp helm-show-completion-overlay)) + (delete-overlay helm-show-completion-overlay) + (remove-hook 'helm-move-selection-after-hook 'helm-show-completion) + (expand-file-name default-preselection)) + ;; Default. + (t (expand-file-name default-preselection))))))) +(put 'helm-quit-and-find-file 'helm-only t) + +(defun helm-generic-sort-fn (s1 s2) + "Sort predicate function for helm candidates. +Args S1 and S2 can be single or \(display . real\) candidates, +that is sorting is done against real value of candidate." + (let* ((qpattern (regexp-quote helm-pattern)) + (reg1 (concat "\\_<" qpattern "\\_>")) + (reg2 (concat "\\_<" qpattern)) + (reg3 helm-pattern) + (split (helm-remove-if-match + "\\`!" (helm-mm-split-pattern helm-pattern))) + (str1 (if (consp s1) (cdr s1) s1)) + (str2 (if (consp s2) (cdr s2) s2)) + (score (lambda (str r1 r2 r3 lst) + (+ (if (string-match (concat "\\`" qpattern) str) 1 0) + (cond ((string-match r1 str) 5) + ((and (string-match " " qpattern) + (string-match + (concat "\\_<" (regexp-quote (car lst))) str) + (cl-loop for r in (cdr lst) + always (string-match r str))) + 4) + ((and (string-match " " qpattern) + (cl-loop for r in lst + always (string-match r str))) + 3) + ((string-match r2 str) 2) + ((string-match r3 str) 1) + (t 0))))) + (sc1 (funcall score str1 reg1 reg2 reg3 split)) + (sc2 (funcall score str2 reg1 reg2 reg3 split))) + (cond ((or (zerop (string-width qpattern)) + (and (zerop sc1) (zerop sc2))) + (string-lessp str1 str2)) + ((= sc1 sc2) + (< (length str1) (length str2))) + (t (> sc1 sc2))))) + +(cl-defun helm-file-human-size (size &optional (kbsize helm-default-kbsize)) + "Return a string showing SIZE of a file in human readable form. +SIZE can be an integer or a float depending it's value. +`file-attributes' will take care of that to avoid overflow error. +KBSIZE is a floating point number, defaulting to `helm-default-kbsize'." + (cl-loop with result = (cons "B" size) + for i in '("k" "M" "G" "T" "P" "E" "Z" "Y") + while (>= (cdr result) kbsize) + do (setq result (cons i (/ (cdr result) kbsize))) + finally return + (helm-acase (car result) + ("B" (format "%s" size)) + (t (format "%.1f%s" (cdr result) it))))) + +(cl-defun helm-file-attributes + (file &key type links uid gid access-time modif-time + status size mode gid-change inode device-num dired human-size + mode-type mode-owner mode-group mode-other (string t)) + "Return `file-attributes' elements of FILE separately according to key value. +Availables keys are: +- TYPE: Same as nth 0 `files-attributes' if STRING is nil + otherwise return either symlink, directory or file (default). +- LINKS: See nth 1 `files-attributes'. +- UID: See nth 2 `files-attributes'. +- GID: See nth 3 `files-attributes'. +- ACCESS-TIME: See nth 4 `files-attributes', however format time + when STRING is non--nil (the default). +- MODIF-TIME: See nth 5 `files-attributes', same as above. +- STATUS: See nth 6 `files-attributes', same as above. +- SIZE: See nth 7 `files-attributes'. +- MODE: See nth 8 `files-attributes'. +- GID-CHANGE: See nth 9 `files-attributes'. +- INODE: See nth 10 `files-attributes'. +- DEVICE-NUM: See nth 11 `files-attributes'. +- DIRED: A line similar to what 'ls -l' return. +- HUMAN-SIZE: The size in human form, see `helm-file-human-size'. +- MODE-TYPE, mode-owner,mode-group, mode-other: Split what + nth 7 `files-attributes' return in four categories. +- STRING: When non--nil (default) `helm-file-attributes' return + more friendly values. +If you want the same behavior as `files-attributes' , +\(but with return values in proplist\) use a nil value for STRING. +However when STRING is non--nil, time and type value are different from what +you have in `file-attributes'." + (helm-aif (file-attributes file string) + (let* ((all (cl-destructuring-bind + (type links uid gid access-time modif-time + status size mode gid-change inode device-num) + it + (list :type (if string + (cond ((stringp type) "symlink") ; fname + (type "directory") ; t + (t "file")) ; nil + type) + :links links + :uid uid + :gid gid + :access-time (if string + (format-time-string + "%Y-%m-%d %R" access-time) + access-time) + :modif-time (if string + (format-time-string + "%Y-%m-%d %R" modif-time) + modif-time) + :status (if string + (format-time-string + "%Y-%m-%d %R" status) + status) + :size size + :mode mode + :gid-change gid-change + :inode inode + :device-num device-num))) + (modes (helm-split-mode-file-attributes (cl-getf all :mode)))) + (cond (type (cl-getf all :type)) + (links (cl-getf all :links)) + (uid (cl-getf all :uid)) + (gid (cl-getf all :gid)) + (access-time (cl-getf all :access-time)) + (modif-time (cl-getf all :modif-time)) + (status (cl-getf all :status)) + (size (cl-getf all :size)) + (mode (cl-getf all :mode)) + (gid-change (cl-getf all :gid-change)) + (inode (cl-getf all :inode)) + (device-num (cl-getf all :device-num)) + (dired (concat + (helm-split-mode-file-attributes + (cl-getf all :mode) t) " " + (number-to-string (cl-getf all :links)) " " + (cl-getf all :uid) ":" + (cl-getf all :gid) " " + (if human-size + (helm-file-human-size (cl-getf all :size)) + (int-to-string (cl-getf all :size))) " " + (cl-getf all :modif-time))) + (human-size (helm-file-human-size (cl-getf all :size))) + (mode-type (cl-getf modes :mode-type)) + (mode-owner (cl-getf modes :user)) + (mode-group (cl-getf modes :group)) + (mode-other (cl-getf modes :other)) + (t (append all modes)))))) + +(defun helm-split-mode-file-attributes (str &optional string) + "Split mode file attributes STR into a proplist. +If STRING is non--nil return instead a space separated string." + (cl-loop with type = (substring str 0 1) + with cdr = (substring str 1) + for i across cdr + for count from 1 + if (<= count 3) + concat (string i) into user + if (and (> count 3) (<= count 6)) + concat (string i) into group + if (and (> count 6) (<= count 9)) + concat (string i) into other + finally return + (if string + (mapconcat 'identity (list type user group other) " ") + (list :mode-type type :user user :group group :other other)))) + +(defun helm-format-columns-of-files (files) + "Same as `dired-format-columns-of-files'. +Inlined here for compatibility." + (let ((beg (point))) + (completion--insert-strings files) + (put-text-property beg (point) 'mouse-face nil))) + +(defmacro with-helm-display-marked-candidates (buffer-or-name candidates &rest body) + (declare (indent 0) (debug t)) + (helm-with-gensyms (buffer window) + `(let* ((,buffer (temp-buffer-window-setup ,buffer-or-name)) + (helm-always-two-windows t) + (helm-split-window-default-side + (if (eq helm-split-window-default-side 'same) + 'below helm-split-window-default-side)) + helm-split-window-inside-p + helm-reuse-last-window-split-state + ,window) + (with-current-buffer ,buffer + (helm-format-columns-of-files ,candidates)) + (unwind-protect + (with-selected-window + (setq ,window (temp-buffer-window-show + ,buffer + '(display-buffer-below-selected + (window-height . fit-window-to-buffer)))) + (progn ,@body)) + (quit-window 'kill ,window))))) + +;;; Persistent Action Helpers +;; +;; +;; Internal +(defvar helm-match-line-overlay nil) +(defvar helm--match-item-overlays nil) + +(defun helm-highlight-current-line (&optional start end buf face) + "Highlight and underline current position" + (let* ((start (or start (line-beginning-position))) + (end (or end (1+ (line-end-position)))) + start-match end-match + (args (list start end buf)) + (case-fold-search (if helm-alive-p + (helm-set-case-fold-search) + case-fold-search))) + ;; Highlight the current line. + (if (not helm-match-line-overlay) + (setq helm-match-line-overlay (apply 'make-overlay args)) + (apply 'move-overlay helm-match-line-overlay args)) + (overlay-put helm-match-line-overlay + 'face (or face 'helm-selection-line)) + ;; Now highlight matches only if we are in helm session, we are + ;; maybe coming from helm-grep-mode or helm-moccur-mode buffers. + (when helm-alive-p + (if (or (null helm-highlight-matches-around-point-max-lines) + (zerop helm-highlight-matches-around-point-max-lines)) + (setq start-match start + end-match end) + (setq start-match + (save-excursion + (forward-line + (- helm-highlight-matches-around-point-max-lines)) + (point-at-bol)) + end-match + (save-excursion + (forward-line + helm-highlight-matches-around-point-max-lines) + (point-at-bol)))) + (catch 'empty-line + (cl-loop with ov + for r in (helm-remove-if-match + "\\`!" (helm-mm-split-pattern + (if (with-helm-buffer + ;; Needed for highlighting AG matches. + (assq 'pcre (helm-get-current-source))) + (helm--translate-pcre-to-elisp helm-input) + helm-input))) + do (save-excursion + (goto-char start-match) + (while (condition-case _err + (if helm-migemo-mode + (helm-mm-migemo-forward r end-match t) + (re-search-forward r end-match t)) + (invalid-regexp nil)) + (let ((s (match-beginning 0)) + (e (match-end 0))) + (if (= s e) + (throw 'empty-line nil) + (push (setq ov (make-overlay s e)) + helm--match-item-overlays) + (overlay-put ov 'face 'helm-match-item) + (overlay-put ov 'priority 1)))))))) + (recenter))) + +(defun helm--translate-pcre-to-elisp (regexp) + "Should translate pcre REGEXP to elisp regexp. +Assume regexp is a pcre based regexp." + (with-temp-buffer + (insert " " regexp " ") + (goto-char (point-min)) + (save-excursion + ;; match (){}| unquoted + (helm-awhile (and (re-search-forward "\\([(){}|]\\)" nil t) + (match-string 1)) + (let ((pos (match-beginning 1))) + (if (eql (char-before pos) ?\\) + (delete-region pos (1- pos)) + (replace-match (concat "\\" it) t t nil 1))))) + ;; match \s or \S + (helm-awhile (and (re-search-forward "\\S\\?\\(\\s\\[sS]\\)[^-]" nil t) + (match-string 1)) + (replace-match (concat it "-") t t nil 1)) + (buffer-substring (1+ (point-min)) (1- (point-max))))) + +(defun helm-match-line-cleanup () + (when helm-match-line-overlay + (delete-overlay helm-match-line-overlay) + (setq helm-match-line-overlay nil)) + (when helm--match-item-overlays + (mapc 'delete-overlay helm--match-item-overlays))) + +(defun helm-match-line-cleanup-maybe () + (when (helm-empty-buffer-p) + (helm-match-line-cleanup))) + +(defun helm-match-line-update () + (when helm-match-line-overlay + (delete-overlay helm-match-line-overlay) + (helm-highlight-current-line))) + +(defun helm-persistent-autoresize-hook () + (when (and helm-buffers-to-resize-on-pa + (member helm-buffer helm-buffers-to-resize-on-pa) + (eq helm-split-window-state 'vertical)) + (set-window-text-height (helm-window) helm-resize-on-pa-text-height))) + +(defun helm-match-line-cleanup-pulse () + (run-with-timer 0.3 nil #'helm-match-line-cleanup)) + +(add-hook 'helm-after-update-hook 'helm-match-line-cleanup-maybe) +(add-hook 'helm-after-persistent-action-hook 'helm-persistent-autoresize-hook) +(add-hook 'helm-cleanup-hook 'helm-match-line-cleanup) +(add-hook 'helm-after-action-hook 'helm-match-line-cleanup-pulse) +(add-hook 'helm-after-persistent-action-hook 'helm-match-line-update) + +;;; Popup buffer-name or filename in grep/moccur/imenu-all. +;; +(defvar helm--show-help-echo-timer nil) + +(defun helm-cancel-help-echo-timer () + (when helm--show-help-echo-timer + (cancel-timer helm--show-help-echo-timer) + (setq helm--show-help-echo-timer nil))) + +(defun helm-maybe-show-help-echo () + (when helm--show-help-echo-timer + (cancel-timer helm--show-help-echo-timer) + (setq helm--show-help-echo-timer nil)) + (when (and helm-alive-p + helm-popup-tip-mode + (member (assoc-default 'name (helm-get-current-source)) + helm-sources-using-help-echo-popup)) + (setq helm--show-help-echo-timer + (run-with-timer + 1 nil + (lambda () + (save-selected-window + (with-helm-window + (helm-aif (get-text-property (point-at-bol) 'help-echo) + (popup-tip (concat " " (abbreviate-file-name + (replace-regexp-in-string "\n.*" "" it))) + :around nil + :point (save-excursion + (end-of-visual-line) (point))))))))))) + +;;;###autoload +(define-minor-mode helm-popup-tip-mode + "Show help-echo informations in a popup tip at end of line." + :global t + (require 'popup) + (if helm-popup-tip-mode + (progn + (add-hook 'helm-move-selection-after-hook 'helm-maybe-show-help-echo) + (add-hook 'helm-cleanup-hook 'helm-cancel-help-echo-timer)) + (remove-hook 'helm-move-selection-after-hook 'helm-maybe-show-help-echo) + (remove-hook 'helm-cleanup-hook 'helm-cancel-help-echo-timer))) + +(defun helm-open-file-with-default-tool (file) + "Open FILE with the default tool on this platform." + (let (process-connection-type) + (if (eq system-type 'windows-nt) + (helm-w32-shell-execute-open-file file) + (start-process "helm-open-file-with-default-tool" + nil + (cond ((eq system-type 'gnu/linux) + "xdg-open") + ((or (eq system-type 'darwin) ;; Mac OS X + (eq system-type 'macos)) ;; Mac OS 9 + "open")) + file)))) + +(defun helm-open-dired (file) + "Opens a dired buffer in FILE's directory. If FILE is a +directory, open this directory." + (if (file-directory-p file) + (dired file) + (dired (file-name-directory file)) + (dired-goto-file file))) + +(defun helm-require-or-error (feature function) + (or (require feature nil t) + (error "Need %s to use `%s'." feature function))) + +(defun helm-find-file-as-root (candidate) + (let* ((buf (helm-basename candidate)) + (host (file-remote-p candidate 'host)) + (remote-path (format "/%s:%s:%s" + helm-su-or-sudo + (or host "") + (expand-file-name + (if host + (file-remote-p candidate 'localname) + candidate)))) + non-essential) + (if (buffer-live-p (get-buffer buf)) + (progn + (set-buffer buf) + (find-alternate-file remote-path)) + (find-file remote-path)))) + +(defun helm-find-many-files (_ignore) + "Simple action that run `find-file' on marked candidates. +Run `helm-find-many-files-after-hook' at end" + (let ((helm--reading-passwd-or-string t)) + (mapc 'find-file (helm-marked-candidates)) + (helm-log-run-hook 'helm-find-many-files-after-hook))) + +(defun helm-read-repeat-string (prompt &optional count) + "Prompt as many time PROMPT is not empty. +If COUNT is non--nil add a number after each prompt." + (cl-loop with elm + while (not (string= elm "")) + for n from 1 + do (when count + (setq prompt (concat prompt (int-to-string n) ": "))) + collect (setq elm (helm-read-string prompt)) into lis + finally return (remove "" lis))) + +(defun helm-html-bookmarks-to-alist (file url-regexp bmk-regexp) + "Parse html bookmark FILE and return an alist with (title . url) as elements." + (let (bookmarks-alist url title) + (with-temp-buffer + (insert-file-contents file) + (goto-char (point-min)) + (while (re-search-forward "href=\\|^ *
+ +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Code: + +(require 'helm-for-files) + + +;;; List of files gleaned from every dired buffer +;; +;; +(defun helm-files-in-all-dired-candidates () + (save-excursion + (cl-loop for (f . b) in dired-buffers + when (buffer-live-p b) + append (let ((dir (with-current-buffer b dired-directory))) + (if (listp dir) (cdr dir) + (directory-files f t dired-re-no-dot)))))) + +;; (dired '("~/" "~/.emacs.d/.emacs-custom.el" "~/.emacs.d/.emacs.bmk")) + +(defclass helm-files-dired-source (helm-source-sync helm-type-file) + ((candidates :initform #'helm-files-in-all-dired-candidates))) + +(defvar helm-source-files-in-all-dired + (helm-make-source "Files in all dired buffer." 'helm-files-dired-source)) + +;;; session.el files +;; +;; session (http://emacs-session.sourceforge.net/) is an alternative to +;; recentf that saves recent file history and much more. +(defvar session-file-alist) +(defclass helm-source-session-class (helm-source-sync) + ((candidates :initform (lambda () + (cl-delete-if-not + (lambda (f) + (or (string-match helm-tramp-file-name-regexp f) + (file-exists-p f))) + (mapcar 'car session-file-alist)))) + (keymap :initform helm-generic-files-map) + (help-message :initform helm-generic-file-help-message) + (action :initform 'helm-type-file-actions))) + +(defvar helm-source-session nil + "File list from emacs-session.") + +(defcustom helm-session-fuzzy-match nil + "Enable fuzzy matching in `helm-source-session' when non--nil." + :group 'helm-files + :type 'boolean + :set (lambda (var val) + (set var val) + (setq helm-source-session + (helm-make-source "Session" 'helm-source-session-class + :fuzzy-match val)))) + + +;;; External searching file tools. +;; +;; Tracker desktop search + +(defun helm-source-tracker-transformer (candidates _source) + ;; loop through tracker candidates selecting out file:// lines + ;; then select part after file:// and url decode to get straight filenames + (cl-loop for cand in candidates + when (and (stringp cand) + (string-match "\\`[[:space:]]*file://\\(.*\\)" cand)) + collect (url-unhex-string (match-string 1 cand)))) + +(defvar helm-source-tracker-search + (helm-build-async-source "Tracker Search" + :candidates-process + (lambda () + ;; the tracker-search command has been deprecated, now invoke via tracker + ;; also, disable the contextual snippets which we don't currently use + (start-process "tracker-search-process" nil + "tracker" "search" + "--disable-snippets" + "--disable-color" + "--limit=512" + helm-pattern)) + ;; new simplified transformer of tracker search results + :filtered-candidate-transformer #'helm-source-tracker-transformer + ;;(multiline) ; https://github.com/emacs-helm/helm/issues/529 + :keymap helm-generic-files-map + :action 'helm-type-file-actions + :action-transformer '(helm-transform-file-load-el + helm-transform-file-browse-url) + :requires-pattern 3) + "Source for retrieving files matching the current input pattern +with the tracker desktop search.") + +;; Spotlight (MacOS X desktop search) +(defclass helm-mac-spotlight-source (helm-source-async helm-type-file) + ((candidates-process :initform + (lambda () + (start-process + "mdfind-process" nil "mdfind" helm-pattern))) + (requires-pattern :initform 3))) + +(defvar helm-source-mac-spotlight + (helm-make-source "mdfind" 'helm-mac-spotlight-source) + "Source for retrieving files via Spotlight's command line +utility mdfind.") + +(provide 'helm-x-files) + +;; Local Variables: +;; byte-compile-warnings: (not obsolete) +;; coding: utf-8 +;; indent-tabs-mode: nil +;; End: + +;;; helm-x-files.el ends here