I use Colemak keyboard layout and the conventional Vim 'hjkl' are not comfortable. In my .vimrc I've added the following to replace 'hjkl' with 'neio' (and vice versa).
noremap n h
noremap e j
noremap i k
noremap o l
noremap h n
noremap j e
noremap k i
noremap l o
noremap N H
noremap E J
noremap I K
noremap O l
noremap H N
noremap J E
noremap K I
noremap L O
If possible, how can I do this in Emacs with Spacemacs?
Here's how hjkl are bound in evil-maps.el:
(define-key evil-motion-state-map "h" 'evil-backward-char)
(define-key evil-motion-state-map "j" 'evil-next-line)
(define-key evil-motion-state-map "k" 'evil-previous-line)
(define-key evil-motion-state-map "l" 'evil-forward-char)
You can put similar lines with your own keys in your init.el to bind the directions to whichever keys you want. You'll also need to rebind hjkl, assuming you don't want them left to their original direction bindings.
EDIT: to replace hjkl with neio I believe you'll need to unbind i and o in evil-normal-state-map:
(define-key evil-normal-state-map "i" nil)
(define-key evil-normal-state-map "o" nil)
hjkl in qwerty is hnei in colemak, not neio. i see why you may want to use neio since that brings all arrows right under your fingers (instead of shifted one position to the left), but this is not necessarily a good thing: down/up (jk on qwerty) are frequently used, and use the two strongest fingers.
qwerty hjkl (colemak hnei) is actually pretty ergonomical, so for me it makes sense to keep this when using colemak. and of course unlearning many years of muscle memory is another reason to stick with it.
keeping hnei for navigation and sensibly dealing with the consequences is exactly what i achieved with my evil-colemak-basics package. you may want to check out its documentation since it has an extensive write-up about the design. perhaps you will even end up using it. :)
You can also make these changes in .spacemacs. I couldn't find the
evil-maps.el, but the FAQ recommends changing them in user-config.
(defun dotspacemacs/user-config ()
;; colemak config
;; Make evil-mode up/down operate in screen lines instead of logical lines
(define-key evil-normal-state-map "i" nil)
(define-key evil-normal-state-map "o" nil) ;;neio back,up,down,next
(define-key evil-motion-state-map "i" 'evil-next-visual-line)
(define-key evil-motion-state-map "e" 'evil-previous-visual-line)
(define-key evil-motion-state-map "n" 'evil-backward-char)
(define-key evil-motion-state-map "o" 'evil-forward-char)
;; Also in visual mode
(define-key evil-visual-state-map "i" 'evil-next-visual-line)
(define-key evil-visual-state-map "e" 'evil-previous-visual-line)
Related
I'm trying to override L in evil-motion-state-map (evil-window-bottom) so my custom binding takes precedence in treemacs. However, this doesn't seem to work:
; my-mode.el
(map! :after evil-mode
:map evil-motion-state-map
"L" nil)
Any clue why? should another mode be passed as :after?
evil-motion-state-map is only taking precedence in the treemacs buffer.
You can use :m to map in evil-motion-state-map.
And also you don't the package name is evil not evil-mode.
So maybe like this.
(map! (:after evil
:m "L" nil))
I'm newbie for emacs and i want to change Ctrl-x key to the Ctrl-w.
Is it easy to change? if so, how could I change?
(also, if i want to split buffer vertically (C-x + 3) to (C-w + v), how should i write my .emacs?)
My advice is don't do it. You're fighting a strong convention, and you'll probably be playing whack-a-mole with edge cases.
That said, you can get 95% there with:
(global-set-key (kbd "C-w") ctl-x-map)
Split vertically can be changed with:
(define-key ctl-x-map (kbd "v") #'split-window-right)
Note that these just override the C-w and C-w v key binds. Existing C-x keybinds (except C-x v) are unchanged.
In emacs ido options, the currently selected option is always shown first in the list. When we change e.g. by arrow keys, or C-s / C-r : the whole list is rotated instead of currently selected option moving anywhere. This is very disconcerting for me. To illustrate , assume A, B, C and D are buffers are we are running ido-switch-buffer
Current behaviour
*A* B C D
Press C-s
*B* C D A
Again press C-s
*C* D A B
What I want is
*A* B C D
Press C-s
A *B* C D
Again press C-s
A B *C* D
I tried setting both "ido-rotate" , and "ido-rotate-file-list-default" to nil as well as t, one by one, but nothing changes in this regard. I don't see any other option in customize-group for ido either. How can I make the selected option move instead of the whole list rotating ?
This is for emacs 26.1, built-in ido.
Edit :
With the regular ido mode, I could override the next, previous key-bindings in the following manner :
(define-key ido-buffer-completion-map (kbd "M-)") 'ido-next-match)
With ido-grid-mode, all my attempts to do so are failing. It seems to insist on the hard-coded sets of keys to find next option / previous option.
This is also not working :
(define-key ido-completion-map (kbd "M-)") 'ido-next-match)
Any hints I could make ido-grid-mode let me override keys ?
Ok, found the answer. The package ido-grid-mode is indeed what i need, thanks #jpkotta. There is a trick to getting my keybinding work with it.
(defun ido-my-keys ()
"Add my keybindings for Ido."
(define-key ido-completion-map (kbd "M-)") 'ido-next-match)
(define-key ido-completion-map (kbd "M-)") 'ido-prev-match)
)
(ido-grid-mode t)
(add-hook 'ido-setup-hook 'ido-my-keys)
That is to say - ido-grid-mode has to be started before setup hook is added for key bindings. I was doing it after, or completely outside the setup hook, which was not working.
EDIT : Forgot to mention, there is another trick. Hack the ido-grid-mode itself. Make the following change in ido-grid-mode.el :
;; ('C-s (define-key ido-completion-map (kbd "C-s") #'ido-grid-mode-next))
;; ('C-r (define-key ido-completion-map (kbd "C-r") #'ido-grid-mode-previous))
('C-s (define-key ido-completion-map (kbd "M-)") #'ido-grid-mode-next))
('C-r (define-key ido-completion-map (kbd "M-(") #'ido-grid-mode-previous))
I finally got this to work, but wanted to know if there was an easier way.
I want to bind a key "U" to put spacemacs into insert-mode, but at the start of the text of the line.
(define-key evil-normal-state-map "u" 'evil-insert)
(define-key evil-normal-state-map "U" (lambda ()
(interactive)
(beginning-of-line-text)
(execute-kbd-macro "u")))
Is there an 'evil command to insert mode at start of line? Or a more elegant way to fire 'evil-insert or run multiple commands?
In evil-mode i executes evil-insert and I executes evil-insert-line.
So the simplest rebinding would be:
(define-key evil-normal-state-map "u" 'evil-insert)
(define-key evil-normal-state-map "U" 'evil-insert-line)
Whenever you want to know which keys run which functions just press C-h k and then the keybinding of choice.
In emacs evil-mode, how do I bind a key sequence so that it pre-populates the evil-mode ex command line and positions the cursor? In vim, I can do this:
nnoremap g/r :%s//g<left><left>
In emacs, I tried this (and several variations):
(define-key evil-normal-state-map "g/" nil)
(define-key evil-normal-state-map (kbd "g/r")
(lambda () (interactive) (kbd ":%s/")))
It has no effect, and I don't see any messages after trying the keymap.
It looks like emacs used to have a useful function evil-ex-read-command that sent input to the evil-mode command line:
https://github.com/magnars/.emacs.d/blob/master/site-lisp/evil/evil-ex.el#L554
But that function doesn't seem to be available anymore.
If you mean to bind the key combination
Press and release g
Press and release /
Press and release r
your string in kdb should be "g / r".
Emacs is not based on keystrokes as vim is, but keystrokes are just a means to execute functions. So pressing k in normal mode does not execute the function k (as in vim), but self-insert-char. That means that you do not bind the combination g / r to equal some other keystrokes, but rather to call an arbitrary function. And evil defines an evil-ex function, that does exactly what you want (Actually it's the exact function, that is called, when you press : in normal mode).
Untested but it should work
(define-key evil-normal-state-map (kbd "g / r") (lambda () (evil-ex "%s/")))