emacs equivalent of vim's shift-h and shift-l
Asked Answered
E

6

21

i'm wondering if emacs has these cursor movement commands built in or if i'm going to have to write them or find a snippet somewhere. i find them pretty spiffy and use them in vim regularly. i haven't found them in emacs' documentation so far.

in vim, they look like this: shift-h -> move cursor to the top of the screen shift-m -> move cursor to the middle of the screen shift-l -> move cursor to the bottom of the screen

just to clarify, i'm not looking to move the cursor to the top/bottom of the document, just to the top/bottom of the currently visible part of the document, i.e. the part that's currently being displayed on screen.

i found one of them so far. alt-r seems to be the equivalent of vim's shift-m. it moves the cursor to the first column of the middle line.

Evensong answered 5/10, 2009 at 12:24 Comment(0)
A
30

Use:

  • Alt+0 Alt+r - top of Window
  • Alt+- Alt+r - bottom of Window

Strictly, these should be written as M-0 M-r for the top of the screen and M-- M-r for the bottom of the screen. Where M means the Meta key which is usually mapped to Alt.

I worked out these keystrokes as follows:

M-r runs the command move-to-window-line. I found this out with C-h k M-r, ie. Ctrl+h, k, Alt+r. The key sequence C-h k means tell me what the next key sequence does. It told me the command name and also that you can pass numeric arguments to the command to pick the line you want to go to. If you don't pass any it moves the point to the middle of the window as you have seen.

You pass numeric arguments to commands by typing a number while holding down Meta. A minus sign on its own is taken to mean -1. Now, to move to the top of the screen we want to pass line 0 and for the bottom of the screen line -1. This gives us the key sequences above.

If you want to bind move-to-window-line to a different key look at Joe's answer to this question.

Atony answered 5/10, 2009 at 12:44 Comment(2)
Use: - M-= M-r - Middle of windowColostomy
smartparens binds M-r to sp-splice-sexp-killing-around, so you may find it helpful to change the Emacs default (move-to-window-line-top-bottom) to M-R.Burnett
S
9

The function you wish to use is move-to-window-line, whose definition is:

move-to-window-line is an interactive built-in function in `C source
code'.

It is bound to M-r.
(move-to-window-line arg)

Position point relative to window.
With no argument, position point at center of window.
An argument specifies vertical position within the window;
zero means top of window, negative means relative to bottom of window.

You would call it with a 0 to go to the top of the page and a -1 to go to the bottom of the page. These can be bound to a key with an anonymous function or a named function. Examples of both are given.

Anonymous Functions

(global-set-key [(f4)] (function
                        (lambda ()
                          "Go to top of page."
                          (interactive)
                          (move-to-window-line 0))))

(global-set-key [(f4)] (function
                        (lambda ()
                          "Go to bottom of page."
                          (interactive)
                          (move-to-window-line -1))))

Named Functions

(defun my-top-of-page ()
  "Go to top of page."
  (interactive)
  (move-to-window-line 0))

(defun my-bottom-of-page ()
  "Go to bottom of page."
  (interactive)
  (move-to-window-line -1))

(global-set-key [(f4)] 'my-top-of-page)
(global-set-key [(shift f4)] 'my-bottom-of-page)
Suite answered 5/10, 2009 at 13:33 Comment(0)
M
7

In Emacs 23.2, M-r does exactly what you want.

The first invocation of this command moves the point to center of the currently visible window, the next successive invocations move to top and bottom.

No additional configuration or custom functions needed.

Mandorla answered 21/5, 2010 at 19:11 Comment(0)
I
2

To add to Joe's and Dave's answers, you can get middle with:

(defun bp-goto-center()
  "move cursor to middle line"
  (interactive)
  (move-to-window-line (/ (window-height) 2)))

(I add bp to the front of all my functions to distinguish them from built-ins, or other people's... feel free to remove that.)

Iguana answered 5/10, 2009 at 13:57 Comment(2)
I would +1 this answer but your code block isn't formatted (yes, I'm pedantic!)Gigue
I needed to do the following to get middle to work,(move-to-window-line (/ (window-buffer-height (get-buffer-window)) 2)).Doze
D
1

I've found that move-to-window-line doesn't respect window-buffer-height. Thus, it doesn't actually provide the behavior Vim has when the buffer size is smaller than the window. Since I don't use Emacs from a terminal, nor do I care about minimizing its frame, I've chosen to reuse its prefix key because the 'z' reminds me of Vim's zt,zm, and zb (and also because I'm going to use the following in combination with Emacs' C-l to achieve the same overall effect).

(define-prefix-command 'ctl-z-map)
(defun move-to-window-line-top ()
  (interactive)
  (move-to-window-line 0))
(defun move-to-window-line-middle ()
  (interactive)
  (let* ((wb-height (window-buffer-height (get-buffer-window)))
        (actual-height (if (> wb-height (window-height))
                           (window-height)
                         wb-height)))
    (move-to-window-line (/ actual-height 2))))
(defun move-to-window-line-bottom ()
  (interactive)
  (move-to-window-line -1)
  (beginning-of-line))
(define-key ctl-z-map (kbd "h") 'move-to-window-line-top)
(define-key ctl-z-map (kbd "m") 'move-to-window-line-middle)
(define-key ctl-z-map (kbd "l") 'move-to-window-line-bottom)
(global-set-key (kbd "C-z") 'ctl-z-map)
Doze answered 12/5, 2012 at 23:49 Comment(0)
G
0

If you are using Emacs 23, it's simply C-l. The first time it will go to the center, the second time it will go to the top, the third time it will go to the bottom.

EDIT:

Oops, my bad, that puts the current line in the center/top/bottom of the window. Still useful though :)

Gravante answered 5/10, 2009 at 13:34 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.