23

I want to be able to use Option-left and Option-right to skip words (and Cmd-left/right to go to beginning and end of lines) within Vim as it does at my shell prompt. My Iterm2 preferences have mappings to do this (e.g. Option-left to Esc-H and a one for option-right to Esc-F to skip over words), and this works in the shell locally or when ssh'd to a remote server.

When I use Vim locally or remotely, option-left works, but option-right does not. I suspect this is because Vim naturally listens for Esc-H, but not Esc-F. I am able to get around this by modifying .vimrc file to Esc-b to b and Esc-f to f, but I don't want to do this to every server I'm connecting to.

Similarly, I have the same desired setup for Cmd-left/right for going to beginning and end of a line. I can get this working in the shell via Iterm2 mappings (e.g. Cmd-left to Esc-[h), but Vim doesn't respond at all to this unless I map keys again (e.g. Esc-[h to ^).

Update: I just figured out how to get option-left/right working. I changed mapping in iTerm2 for these to be escape-[1;5D and escape-[1;5C respectively. I still want to solve the Cmd-left/right problem though (I changed my question's title to reflect this). Any ideas?

Dolan Antenucci
  • 15,432
  • 17
  • 74
  • 100
  • 2
    Neither your shell nor Vim are going to react to the `Cmd` key. Also, as a long time mac user, I find `^$bBeEwW` to be far more efficient: if you are going to use Vim seriously, why not use it as it was designed? – romainl Mar 07 '12 at 06:59
  • @romainl are you sure? It worked for me on linux, Windows and Solaris and across terminal emulators like screen and/or Putty – sehe Mar 07 '12 at 07:49
  • 1
    Yes. Pressing the `Cmd` key is not registered by the shell (no ANSI code for modifier `Cmd`) so AFAIK there is no way to send `Cmd` to Vim which doesn't even understand `Cmd` anyway: it's MacVim-only, no other versions of Vim, CLI or GUI, on any OS, can use `` mappings. So, the only way to use the `Cmd` key in CLI Vim mappings is to swap it with some other key: `Alt`, `Ctrl`, `Shift`, whatever, there are lots of apps/hacks for that. Obviously, doing that may open the door to an avalanche of problems and, *actually* displace the problem since we still have the same number of modifier keys. – romainl Mar 07 '12 at 08:42
  • That's when you see the brilliance of modal editing and single key commands. – romainl Mar 07 '12 at 08:44
  • 1
    I already have iTerm2 mapping Cmd+left/right mapping to other keys, so I don't need Vim to listen for that, but instead, if there is some other Escape/hex code that Vim supports by default as an alterative to "$" and "^", then perhaps I can update my mappings to use that. For example, Home and End keys work on a standard Linux install. Any idea what key-sequence those send? – Dolan Antenucci Mar 07 '12 at 13:51
  • What do you mean? You were asking specifically about sending `Cmd`+something to Vim via iTerm2. Now you say that you already have `Cmd`+`left/right` mapped to other keys (which ones? how?) in iTerm2 and now want to do what with `Home`/`End` and `^`/`$`? Could you explain what it is you want to achieve? What's wrong with Vim's default mappings? – romainl Mar 07 '12 at 14:50
  • @romainl - Vim's mappings are fine, but I prefer for Vim to also support the same behavior of most other Mac applications in that option-left/right skips words, and cmd-left/right goes to beginning/end of lines. Call me a Vim rookie, but I'm set in my ways. My goal is to not modify Vim to support this (since I'd need to add .vimrc entries on all servers I use), but instead to use iTerm2's key-mapping to do this. I believe one way is to have iTerm2 mimic the Home/End keys, which Vim recognizes by default, at least on the Ubuntu installs I've used. Sorry for any confusion – Dolan Antenucci Mar 07 '12 at 15:23
  • So you want iTerm2 to send `$` to Vim when you type `Cmd`+`right` and `^` when you type `Cmd`+`left`. Am I right? I **really** think you shouldn't do that but the solution is extremely easy: in iTerm's prefs, under "Keys", click the `+`, press `Cmd`+`right`, choose "Send text" from the dropdown menu and type `$`. Do the same for your other shortcut and you are set. – romainl Mar 07 '12 at 15:41
  • Problem with mapping `cmd-left/right` to `^/$` is the shell will use the mapping as well. I think using the `Home/End` keys is the way to go, so what I've done is map `cmd-left` to `Escape-[H`, and that works fine in shell, but not in Vim. When I connect a keyboard with a `Home` key, this works in Vim, but if I use the command `read` in Unix/Linux to intercept key combinations of `Cmd-Left` and `Home`, they both output `^[[H`. Any ideas on why Vim sees these two commands differently when `read` sees them as same? – Dolan Antenucci Mar 07 '12 at 23:14
  • I finally figured it out. I'll explain in an answer below. Thanks all for the patience and help! – Dolan Antenucci Mar 08 '12 at 01:16

4 Answers4

25

To mimic OS X's behavior of sending Cmd-left/right to the beginning/end of a line, I add the following mappings in iTerm2:

  • Cmd-left to escape-sequence [1~
  • Cmd-right to escape-sequence [4~

To mimic OS X's behavior of sending Option-left/right to the previous/next word, I add the following mappings in iTerm2:

  • Option-left to escape-sequence [1;5D
  • Option-right to escape-sequence [1;5C

Special thanks to this blog post for tracking down what I was missing with the cmd-left/right mappings

Dolan Antenucci
  • 15,432
  • 17
  • 74
  • 100
  • Note: this doesn't work in my local python shell on OS X, but when ssh'd to linux machine, these work in python shell. No idea why. If I use the mappings ilias mentioned below, they don't work in Vim, but everywhere else, including python they work – Dolan Antenucci Jun 15 '12 at 01:31
  • 1
    The python shell in OS X doesn't use readline unless you install https://pypi.python.org/pypi/readline – Evan Krall Jun 01 '13 at 16:22
  • 1
    This works nice in `vim` but it doesn't work in `bash` (e.g. when writing a long command) :( – Felix Dec 17 '13 at 21:37
  • Hi @DolanAntenucci , what the equivalent mappings would be in .vimrc (my workflow is Terminal.app, tmux, and vim)? Something like map [1;5D and [1;5C ? – skilbjo Jul 17 '16 at 08:29
  • @JohnSkilbeck - I'm not sure anymore what mappings would work in .vimrc; lately I'm just using the standard vim shortcuts along with the iterm changes I mentioned above. Not ideal for me, but just been too lazy to get vim working with these shortcuts – Dolan Antenucci Jul 17 '16 at 13:34
  • Brilliant! Thank you so much, for me it work both in VIM & bash 3 (OS X). – Razvan Grigore Jan 12 '17 at 20:31
  • 4
    Neither this solution, nor Karim's worked for my Cmd-left/right bindings. I had to set `bindkey '^[[1~' beginning-of-line` and `bindkey '^[[4~' end-of-line` in my `~/.zshrc`, then I was able to set the escape codes per this answer. Everything works as expected now in both iTerm2 and Vim. – varcharmander Jan 17 '20 at 03:58
20

I'm using iTerm2 3.4.2 and there's actually a preset that you can select for your profile that enables this. Profile Key Mappings Natural Text Editing Preset

Audisho Sada
  • 311
  • 2
  • 4
11

FWIW, dolan's answer didn't work for me on iTerm 2 1.0.0.20120203 on Mac OS X 10.7.3. His solution only inserted ~ and 5D/5C into my terminal when I pressed the shortcut keys.

Instead, I used the following solutions:

YMMV, not sure why one set of solutions would work and not the other

Community
  • 1
  • 1
Ilias Karim
  • 4,798
  • 3
  • 38
  • 60
  • 1
    I'm running the same versions of iTerm 2 and OS X. I am using "xterm-256color" as my Terminal Type with "Unicode (UTF-8)" as my character encoding. Maybe see if you have a different setting there? – Dolan Antenucci Apr 10 '12 at 12:56
  • I have the same settings. I tried entering your escape codes into both Keys and Profiles > Keys, same effect. Don't know what could be different – Ilias Karim Apr 11 '12 at 10:07
  • I found that your settings and my settings both work on the command line, but I get different behavior with each in Vim and the Python shell. My settings don't work in Python shell (does ~/5D/5C as you mention), and in Vim (default `vim`, not MacVim), your settings trigger some other functionality or don't work depending which command I'm using (e.g cmd-right scrolls window one line). If you get a chance, check out if Vim has the above commands working. Can you also clarify if you get ~/5D/5C at command line – Dolan Antenucci Jun 15 '12 at 01:25
  • As @evan-krall [commented above](http://stackoverflow.com/a/9611698/484127), when readline is used, readline overtakes parsing input (including what to do with escape sequences), so [configuring special keys in it's config file is required](https://code.google.com/p/iterm2/wiki/Keybindings#About_readline). – tutuDajuju Dec 17 '14 at 09:43
1

I don't have MacOS, so I cannot exactly know your situation, but I recognize the problem from other OSes.

Basically, it would mean that the terminal sends keycodes that aren't understood by vim. I fixed it in the past by doing

 TERM=something
 export TERM

before invoking vim

E.g. in order to get all keys and syntax highlighting working on AIX 5.3 across Putty/screen, I needed to use

 TERM=iris-ansi vim

There is a list of builtin terminal types if you pass a bad TERM

sehe
  • 374,641
  • 47
  • 450
  • 633
  • I assume this would require adding this variable on remote servers I connect to. Also, iTerm2 lets me change which terminal type it emulates (currently set to "xterm", but there are others like "xterm256-color"), so maybe I need to switch terminal types? Check out my comment above about why Home/End keys work, and if there is a way to emulate that. Thanks! – Dolan Antenucci Mar 07 '12 at 13:59
  • @dolan AFAIR Putty and ssh have options to 'send' environment variables, which normally makes a lot more sense. I'd suggest fiddling with the TERM types to see wwhat happens – sehe Mar 07 '12 at 16:57