Warum bewegt "ESC" den Cursor in vim zurück?

62

In vim, wenn ich drücke ESC, um in den Befehlsmodus zurückzukehren, bewegt sich der Cursor ein Zeichen nach links. Dies ist nicht das, was ich mir erhoffen würde, gelegentlich drücke ich sofort l, um zu dieser Stelle zurückzukehren, um vielleicht einen Charakter zu löschen.

Gibt es einen Grund für dieses Verhalten? Ist das praktisch für ein Verwendungsmuster, das mir fehlt?

Eric Wilson
quelle
1
Ich habe das bis jetzt noch nie bemerkt ... und ich benutze vim jeden Tag. Ich habe keine Ahnung warum, aber ich bin daran interessiert, die Antworten zu hören.
gabe.
5
Wenn Sie in den Einfügemodus zurückkehren, können Sie beim Einfügen 'a' anstelle von 'i' für das Anhängen drücken. Sie kehren dann zu der Position zurück, in der Sie sich befanden, bevor Sie die Escape-Taste drücken.
Pinguin359

Antworten:

40

Im Einfügemodus befindet sich der Cursor zwischen Zeichen oder vor dem ersten oder nach dem letzten Zeichen. Im normalen Modus befindet sich der Cursor über einem Zeichen (Zeilenumbrüche sind für diesen Zweck keine Zeichen). Dies ist etwas ungewöhnlich: Die meisten Editoren setzen den Cursor immer zwischen Zeichen und lassen die meisten Befehle auf das Zeichen nach dem Cursor (nicht, genau genommen, unter dem Cursor) wirken. Dies ist möglicherweise teilweise auf die Tatsache zurückzuführen, dass Textterminals vor GUIs immer den Cursor auf einem Zeichen zeigten (Unterstreichen oder Blockieren, möglicherweise Blinken). Diese Abstraktion schlägt im Einfügemodus fehl, da dies eine weitere Position erfordert (Pfosten gegen Zäune).

Das Umschalten zwischen den Modi muss den Cursor sozusagen um ein halbes Zeichen bewegen. Der iBefehl bewegt sich nach links, um den Cursor vor das Zeichen zu setzen, über dem er sich befunden hat. Der aBefehl bewegt sich nach rechts. Beim EscVerlassen des Einfügemodus (durch Drücken von ) wird der Cursor nach Möglichkeit nach links verschoben (wenn er sich am Zeilenanfang befindet, wird er stattdessen nach rechts verschoben).

Ich nehme an, das EscVerhalten macht irgendwie Sinn. Oft tippt man am Ende der Zeile und Esckann dort nur nach links gehen. Das allgemeine Verhalten ist also das häufigste Verhalten.

Stellen Sie sich das Zeichen unter dem Cursor als das letzte interessante Zeichen vor und den Befehl Einfügen als a. Sie können wiederholen, a Escohne den Cursor zu bewegen, mit der Ausnahme, dass Sie eine Position nach rechts springen, wenn Sie am Anfang einer nicht leeren Zeile beginnen.

Gilles 'SO - hör auf böse zu sein'
quelle
21

Optisch macht es in gvim mehr Sinn:

Während der Bearbeitung befindet sich der Cursor zwischen den Zeichen:
Bildbeschreibung hier eingeben

Im normalen Modus steht es über dem letzten Zeichen:
Bildbeschreibung hier eingeben

So ist es nicht wirklich ein Zeichen zurückgehen, nur davon , dass zwischen r und szu sein auf r

Martin Ueding
quelle
1
Tolles Bild. Um ehrlich zu sein, bin ich im Lager, das besagt, dass der Charakter mbei der Rückkehr in den normalen Modus hervorgehoben bleiben sollte ...
Steven Lu
Hoppla. Bildlinks sind jetzt tot.
Steven Lu
1
Bildlinks jetzt tot.
Steven Lu
1
Ja, das manuelle Hosten Ihrer Bilder ist sowohl arbeitsintensiver als auch weniger zuverlässig, als nur das Tool im Markdown-Editor auf dieser Site zu verwenden.
Steven Lu
1
Ist bei ihnen wieder alles in Ordnung? Es ist "Cursor", was sie eingegeben haben und Ihr Text erwähnt "j"
Poige
15

Dieses Verhalten kann wie hier beantwortet bearbeitet werden , aber denken Sie eine Sekunde lang darüber nach, was los ist. Wenn Sie sich im Einfügemodus befinden, befinden Sie sich nicht über einem Zeichen, sondern ZWISCHEN diesen. Wenn Sie etwas einfügen, springt der Cursor an das Ende von dem, was Sie eingefügt haben, so dass das nächste eingefügte Objekt danach ist. Denken Sie jetzt darüber nach, ob Sie gerade einen Brief getippt haben und dann etwas damit anfangen wollten. Wenn Sie drücken Esc, wird der Auswahlcursor direkt über das zuletzt eingegebene Zeichen gesetzt. Wenn es dies nicht tun würde, wäre es tatsächlich ziemlich umständlich.

Die Situation, an die Sie wahrscheinlich denken, ist, wenn Sie sich im Einfügemodus wie im normalen Modus bewegen und dann wechseln. In diesem Fall scheint der Cursor ein Zeichen zurück zu gehen, aber wenn Sie so denken, zeigt dies, dass Sie sich im Einfügemodus befanden und das letzte, was Sie getan haben, war NICHT Einfügen. Vielleicht solltest du mehr Zeit im normalen Modus verbringen?

Caleb
quelle
15
Das ergibt für mich keinen Sinn. Wie erklären Sie das Rückwärtsgehen bei wiederholten iund ESCTastendrücken?
Warren Young
4
In den Einfügemodus zu wechseln, nichts einzufügen und ihn dann zu verlassen, ist kein fairer Test. Warum würden Sie sich im Einfügemodus befinden, wenn Sie nichts einfügen würden? Wenn Sie etwas einfügen, bleibt beim Zurückkehren in den normalen Modus das ausgewählte Zeichen erhalten. Sehr intuitiv.
Caleb
4
Es geht nicht um "fair", es geht um Erklärungskraft. Wenn Ihre Betriebstheorie nicht das gesamte Verhalten erklärt, ist es entweder unvollständig oder das Verhalten von vi ist inkonsistent. Ich ziehe es vor zu glauben, dass vi in ​​jeder Hinsicht perfekt und daher konsistent ist. :)
Warren Young
9
@Warren Das "Rückwärtsgehen" von igefolgt von ESCist eine Funktion von iund ist völlig unabhängig von ESC; Wenn Sie auf idrücken, fordern Sie vim auf , ein Zeichen einzufügen , was per Definition "Einfügen eines Zeichens vor dem Zeichen, auf dem ich mich befinde" bedeutet, im Gegensatz zu a"Anhängen eines Zeichens nach dem Zeichen".
Kromey
3
Im Allgemeinen bin ich nach jeder Änderung, wenn ich diese Änderung verlasse, mit dieser Änderung fertig, und das nächste, was ich tun möchte, wird wahrscheinlich eine andere Änderung beinhalten. Wenn ich den Einfügemodus verlasse (unabhängig davon, wie ich ihn eingegeben habe), würde ich im Allgemeinen vorziehen, dass sich der Cursor auf dem nächsten Zeichen befindet, damit ich für meine nächste Änderung bereit bin , anstatt bereit zu sein, das zu ändern, was ich gerade getan habe eingefügt.
Kyle Strand
6

Geben Sie Alt+ ein L, um zum Befehlsmodus zurückzukehren.

Es ist keine Neuzuordnung oder Änderung der VIM-Konfiguration erforderlich. Dies funktioniert, da bei den meisten Terminalemulatoren Alt+ KEYein Escgefolgt von gesendet wird KEY(unter xterm müssen Sie möglicherweise eine Xterm*metaSendsEscape: trueZeile in Ihre ~ / .Xdefaults-Datei einfügen). Mit diesem Verhalten können Sie sogar andere Einfügemoduskombinationen "erstellen", die sofort funktionieren - wie Alt+ Sto Backspace.

Übrigens kann es sehr unpraktisch sein, den Cursor über dem gerade geschriebenen Zeichen zu haben. EscdwLöscht beispielsweise nicht das Wort, das dem gerade eingefügten Text folgt.

user79932
quelle
Die Unannehmlichkeiten, auf die Sie verweisen, können vermieden werden, indem Sie vor dem Escape-Vorgang immer ein Leerzeichen im Einfügemodus eingeben. Dann wird der Cursor, der den Einfügemodus verlässt, über das Leerzeichen gesetzt, und Sie können Esc d edas vorangestellte Wort löschen. Ich kehrte zum Standardverhalten zurück, weil ich das Gefühl hatte, dass es andere Verhaltensweisen veränderte, die bereits in meinem Kopf kodiert waren.
mljrg
4

Hier ist meine Lösung.

Es ist eine knappe Version der Lösung, die auf der Wikia-Seite dazu angeboten wird .

au InsertLeave * call cursor([getpos('.')[1], getpos('.')[2]+1])
Steven Lu
quelle
+1 auch hier, um die Wiki-Seite zu zitieren, obwohl der Benutzer nicht wirklich nach einer Möglichkeit gefragt hat, dieses Verhalten zu ändern.
Kyle Strand
Sie werden bemerken, dass viele Plugins, wenn Sie sich weit genug in Vim vertiefen, auf das Standardverhalten (etwas unintuitiv) angewiesen sind. Wenn Sie also feststellen, dass ein Teil zufällig ein einzelnes Zeichen isst oder zerfetzt, könnte dies dazu führen. Ich benutze diesen Befehl nicht selbst; es funktioniert aber gut.
Steven Lu