Switching to ivy from helm

Table of Contents

I've been using Helm since my Emacs Day 1, and there are many times I think about switching over to Ivy to see what is the different. But looking at my heavily Helm customized in init.el, it scare me off.

So once again, I tried to do it today. Things gone pretty well.

Since this is just a quick note, I'll not go to any details, the below are my steps and config that replaced my everyday usage of Helm by Ivy.

1 Install ivy and counsel

All the packages needed:

;; Ivy and Counsel
(use-package ivy :ensure t
  :diminish (ivy-mode . "")
  (ivy-mode 1)
  (setq enable-recursive-minibuffers t)
  ;; add ‘recentf-mode’ and bookmarks to ‘ivy-switch-buffer’.
  (setq ivy-use-virtual-buffers t)
  ;; number of result lines to display
  (setq ivy-height 10)
  ;; no regexp by default
  (setq ivy-initial-inputs-alist nil)
  ;; configure regexp engine.
  (setq ivy-re-builders-alist
  ;; allow input not in order
        '((t   . ivy--regex-ignore-order))))

(use-package counsel :ensure t)
(use-package counsel-projectile :ensure t)

2 Replacing Helm with Ivy

First, is helm-occur, the replacement is swiper. One thing that need to be note here is, calling swiper alone will not picking up the current selection or symbol at point, which helm-occur do by default, so I have to pass some parameter to swiper.

(global-set-key (kbd "C-s") (lambda () (interactive)
  (swiper (format "%s" (let ((sym (thing-at-point 'symbol))) (if sym sym ""))))))

The same thing with helm-projectile-ag command, I replace it with counsel-rg:

(global-set-key (kbd "C-c s") (lambda () (interactive)
  (counsel-rg (format "%s" (let ((sym (thing-at-point 'symbol))) (if sym sym ""))))))

helm-resume can now be replaced by ivy-resume:

(global-set-key (kbd "C-x .") 'ivy-resume)

And helm-M-x, now we have counsel-M-x for that:

(global-set-key (kbd "C-\\") 'counsel-M-x)

Working with projectile, I replace helm-projectile-find-file and helm-projectile-switch-project with counsel-projectile-find-file and counsel-projectile-switch-project:

(global-set-key (kbd "C-c p p") 'counsel-projectile-switch-project)
(global-set-key (kbd "C-c p f") 'counsel-projectile-find-file)

Everything is the same, just replace the word helm by ivy huh? no, not everyting, helm-show-kill-ring now becomes counsel-yank-pop:

(global-set-key (kbd "C-x p r") 'counsel-yank-pop)

3 What's the different?

First, it is very easy to see that Ivy provides a much more minimal UI, and much more responsive because swiper will jump to the target line right after you navigate to a search result. I don't like both of these things. But it not a deal breaker, still nice to have tho.

What keep me from switching back to Helm is a neat feature called ivy-occur, it's pretty much the same as when you press C-x C-s in a helm-ag search result, it will save the search to a buffer, with ivy-occur the buffer doesn't go away when you visit an entry. So you have a persistent result list on the screen (again, just like what Vim have for a long time already).

In my previous config, helm-ag perform much more faster because I replaced the helm-ag-base-command by ripgrep, and both counsel-ag or counsel-rg are much slower, with a couple of seconds delay.

Overally, the switch is easy, and Ivy is not so bad, I think I'm gonna stick with it for a while then.

Date: 2019-04-24 Wed 00:00

Author: Huy Tran

Created: 2019-04-24 Wed 12:18