5.4 KiB
Emacs Control Via Ivy
,#+ARROYO_EMACS_MODULE: ivy-config
(provide 'cce/ivy-config)
Ivy is a Tool for interactive text completion in Emacs. It's built for quick string matching within a list of completion candidates, such as commands to run, the auto-completion value for a function signature, et cetera. It's a replacement for a large swath of Emacs functionality, making it quicker and more intuitive to work with than it is with the default interface, and a bit more responsive than, in my experience, than Helm.
Out of the box, Ivy does little more than replace ido
functionality, but there are a wealth of connectors, both in the collection of Counsel commands in the package, and elsewhere within ELPA, GitHub and the rest of the Emacs ecosystem. Here I configure the base commands, and in sister documents I will configure specific functionalities past that.
In short:
- Install Ivy
- configure Magit and Projectile to use it.
- bind
C-x b
and<NORMAL><SPC>b
toivy-switch-buffer
- bind
M-u
toivy-resume
which will re-display any previous Ivy command and possibly re-start it (this works with Counsel commands at least)
(use-package ivy
:demand
:config
(ivy-mode 1)
(setq ivy-height 15
projectile-completion-system 'ivy
magit-completing-read-funciton 'ivy-completing-read)
:bind
("M-u" . ivy-resume)
("C-x b" . ivy-switch-buffer)
:bind (:map evil-leader--default-map
("b" . 'ivy-switch-buffer))
:diminish ivy-mode)
In short:
counsel-find-files
and related commands will auto-fill if there is a file under the cursor.- Ignore files that end with a
~
or start with a.
, or end or start with a#
. - Bind
/
and?
to Swiper in Normal Mode - Bind
<NORMAL><SPC><SPC>
andM-x
tocounsel-M-x
, which is an interactive command launcher but with Ivy - Bind
C-c C-q
to a tag selector inorg-mode
andorg-agenda
.
(use-package counsel
:demand
:after (org org-agenda ivy)
:commands (counsel-M-x swiper swiper-backward counsel-org-tag counsel-org-tag-agenda)
:config
(setq counsel-find-file-at-point t
counsel-find-file-ignore-regexp (concat "\\(?:\\`[#.]\\)" "\\|\\(?:[#~]\\'\\)"))
:bind (:map evil-leader--default-map ;; prefix to SPC
("<SPC>" . counsel-M-x))
(:map evil-normal-state-map ;; evil normal mode
("/" . swiper)
("?" . swiper-backward))
(:map org-mode-map ;; org-mode
("C-c C-q" . counsel-org-tag))
(:map org-agenda-mode-map ;; org-agenda
("C-c C-q" . counsel-org-tag-agenda))
:bind ;; global keys
("M-x" . counsel-M-x)
("C-x C-f" . counsel-find-file)
("C-x d" . counsel-dired)
("M-`" . counsel-tmm)
:diminish counsel-mode)
I have a special Hydra interface, which exposes some common Ivy actions in a Hydra which I can access from within Ivy itself. I should source this code properly, it's not a thing I wrote, it may've been lifted from the Ivy documentation.
(defun ivy--matcher-desc () ; used in `hydra-ivy'
(if (eq ivy--regex-function
'ivy--regex-fuzzy)
"fuzzy"
"ivy"))
(defhydra hydra-ivy (:hint nil :color pink)
"
^^_,_ _f_ollow occ_u_r _g_o ^^_c_alling %-7s(if ivy-calling \"on\" \"off\") _w_/_s_/_a_: %-14s(ivy-action-name)
_p_/_n_ _d_one ^^ _i_nsert ^^_m_atcher %-7s(ivy--matcher-desc)^^^^^^^^^^^^ _C_ase-fold: %-10`ivy-case-fold-search
^^_._ _D_o it! ^^ _q_uit _<_/_>_ shrink/grow^^^^^^^^^^^^^^^^^^^^^^^^^^^^ _t_runcate: %-11`truncate-lines
"
;; arrows
("," ivy-beginning-of-buffer) ; default h
("p" ivy-previous-line) ; default j
("n" ivy-next-line) ; default k
("." ivy-end-of-buffer) ; default l
;; quit ivy
("q" keyboard-escape-quit :exit t) ; default o
("C-g" keyboard-escape-quit :exit t)
;; quit hydra
("i" nil)
("C-o" nil)
;; actions
("f" ivy-alt-done :exit nil)
;; Exchange the default bindings for C-j and C-m
("C-m" ivy-alt-done :exit nil) ; RET, default C-j
("C-j" ivy-done :exit t) ; default C-m
("d" ivy-done :exit t)
("g" ivy-call)
("D" ivy-immediate-done :exit t)
("c" ivy-toggle-calling)
("m" ivy-toggle-fuzzy)
(">" ivy-minibuffer-grow)
("<" ivy-minibuffer-shrink)
("w" ivy-prev-action)
("s" ivy-next-action)
("a" ivy-read-action)
("t" (setq truncate-lines (not truncate-lines)))
("C" ivy-toggle-case-fold)
("u" ivy-occur :exit t))
(with-eval-after-load 'ivy
(define-key ivy-minibuffer-map (kbd "C-m") 'ivy-alt-done) ; RET, default C-j
(define-key ivy-minibuffer-map (kbd "C-j") 'ivy-done) ; default C-m
(define-key ivy-minibuffer-map (kbd "C-S-m") 'ivy-immediate-done)
(define-key ivy-minibuffer-map (kbd "C-t") 'ivy-toggle-fuzzy)
(define-key ivy-minibuffer-map (kbd "C-o") 'hydra-ivy/body))