0

I read in evil wiki that I can change prefix keys such as C-c or C-x and so on to cc, cx, but I'm not experienced in Elisp and I tried a lot of variants but I can only define c as C-c but not a cc to C-c here is my evil.el file. What do I need to change in my evil.el or maybe in init.el to set cc as C-c and cx as C-x?

My evil.el file:

  (defvar evilPackages
  '(goto-chg
    evil-magit
    evil-matchit
    evil-escape))

(mapc #'(lambda (package)
    (unless (package-installed-p package)
      (package-install package)))
      evilPackages)

;; Undo-tree (as dependency of Evil)
(add-to-list 'load-path "~/.emacs.d/undo-tree")
(global-undo-tree-mode)

(use-package evil
  :ensure t
  :init
  (setq evil-want-C-u-scroll t)
  (setq evil-want-integration t) ;; This is optional since it's already set to t by default.
  (setq evil-want-keybinding nil)
  (require 'evil-magit)
  (require 'evil-matchit)
  (global-evil-matchit-mode 1)
 :config
  (evil-mode 1)
  (setq-default evil-escape-key-sequence "jk")
  (evil-escape-mode t))

(use-package evil-collection
  :after evil
  :ensure t
  :config
  (evil-collection-init))
1
+50

Generally, I recommend to avoid key translating in emacs. I know it's common in vim but in emacs I think it's better to map your actions using modes and commands. That's because, in contrast to vim, everything in emacs is a command, so you don't really need to rely on key translation. You can check which command a key stroke is bound to with F1 k [key]. If you specify the reasons you need to do this we might help you with a better solution.

That said, the following code should do what you wish:

(defun my/c-c ()
  (interactive)
  (setq unread-command-events (listify-key-sequence (kbd "C-c"))))

(defun my/c-x ()
  (interactive)
  (setq unread-command-events (listify-key-sequence (kbd "C-x"))))

(evil-define-key 'normal global-map (kbd "cc") 'my/c-c)
(evil-define-key 'normal global-map (kbd "cx") 'my/c-x)

EDIT: If you want to rebind all ctrl keys, you could loop thourgh all the letters and map them like this:

(defun my/c-bind (letter)
  (let* ((l letter))
    (evil-define-key 'normal global-map (concat "c" letter)
      `(lambda () (interactive)
         (setq unread-command-events
               (listify-key-sequence (kbd (concat "C-" ',l))))))))

;; bind all looping from a to z
(defun my/c-bind-all()
  (let ((char 97))
    (while (< char 123)
      (my/c-bind (char-to-string char))
      (setq char (+ char 1)))))

(my/c-bind-all)

If you don't want every ctrl combination rebound, instead of using my/c-bind-all you could also bind keys individually with my/c-bind:

(my/c-bind "c") ;; bind 'cc' to ctrl-c
(my/c-bind "x") ;; bind 'cx' to ctrl-x
| improve this answer | |
  • It's pretty good and works fine, but I expected something like cx where x can be any character, like super() in normal global-map, to avoid using C-c C-g C-x and so on, because its hard for hands to do it all day, my keys were rebind to caps_lock or to cmd or to any other key, anyway its really hard for hands. – Alexandr S. Mar 26 '19 at 13:09
  • 1
    @om2c0de I edited my answer with a dynamic solution. Is that what you need? – Jesse Mar 26 '19 at 14:42
  • Wow, you are like the elisp ninja!! Of course, this bounty will be yours, just last question - Does it really complex to watch for c(pressed) events like C-x f can be a cxf ? – Alexandr S. Mar 26 '19 at 14:51
  • Nah, I'm a elisp beginner. I just learn as I go, no rush. I don't understand your question. You mean cxf to be C-x C-f? Because cxf already should behave like C-x f – Jesse Mar 26 '19 at 14:59
  • Yeah, so if i'm pressing "c" => c-x c-f as cxf, but if I just pressed once "c" => cxf as C-x f, Do you understand me? ;) – Alexandr S. Mar 26 '19 at 15:15

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.