Pare no início de uma palavra em `forward-word`

17

Costumo usar várias invocações forward-wordseguidas por uma única backward-wordpara mover o ponto para o início de uma palavra em uma linha. Acho que nunca me acostumei com a maneira como forward-worddifere do vim we, mesmo depois de anos usando o Emacs, não consigo me acostumar com a diferença.

Existe uma função que eu poderia usar em vez de forward-wordnão pular sobre as palavras, mas parar no início de uma palavra também? Existem outras estratégias para avançar para o início de uma palavra ao avançar um ponto que não envolva a execução repetida forward-char?

rekado
fonte
Você pode (em algum momento) estar interessado em escrever sua própria palavra / parágrafo de avanço / retrocesso e funções de kill-word relacionadas. A seguir, estão três links para algumas funções personalizadas que uso diariamente - o comportamento se assemelha a certos processadores de texto que usei ao longo dos anos: stackoverflow.com/a/20456861/2112489 | stackoverflow.com/q/18675201/2112489 | superuser.com/a/685604/206164
lawlist

Respostas:

24

O miscpacote (enviado com o emacs) possui a função interna forward-to-word, que faz o que eu acho que você deseja:

forward-to-word is an interactive compiled Lisp function in `misc.el'.

It is bound to M-f.

(forward-to-word ARG)

Move forward until encountering the beginning of a word.
With argument, do this that many times.

Para usá-lo, primeiro adicione (require 'misc)ao seu arquivo de configuração.

descontinuada
fonte
Obrigado, isso é útil. Infelizmente, isso também não para no final de uma palavra.
rekado
1
É verdade, mas o vim também não w. Tanto quanto eu posso ver, existe um mapeamento quase perfeito do vim para o emacs: w= forward-to-word; e= forward-word; b= backward-word; ge= backward-to-word. Mas eu não sou um usuário especialista em vim, então talvez exista alguma sutileza.
preterido
Heh, você está de fato certo. Eu acho que sempre que estou no vim w, ee bsimplesmente me afasto e me movo. Esquisito. Eu tinha certeza que wparei nos dois pontos! Então, eu vou aceitar sua resposta, porque ele se encaixa exatamente a minha pergunta :)
rekado
4

Você pode vincular a seguir função M-fe ligam o original forward-wordpara M-F. Esta função simplesmente pega arge passa para a forward-wordfunção. Portanto, os argumentos universais funcionarão tão bem quanto com a função original.

(defun modi/forward-word-begin (arg)
  "Move forward a word and end up with the point being at the beginning of the
next word.  Move point forward ARG words (backward if ARG is negative).
If ARG is omitted or nil, move point forward one word."
  (interactive "p")
  (forward-word arg)
  (forward-word 1)
  (backward-word 1))

Atenção, porém, que a função acima nem sempre pode fazer a coisa certa ; depende muito se o ponto já está no início de uma palavra ou não.


Aqui está outra maneira de implementar o acima, onde o limite da palavra não é conforme a tabela de sintaxe, mas estritamente na separação de espaço em branco:

(defun modi/forward-word-begin (arg)
  "Move forward ARG (defaults to 1) number of words.
Here 'words' are defined as characters separated by whitespace."
  (interactive "p")
  (dotimes (_ arg)
    (forward-whitespace 1)))

O crédito vai para @glucas para essa ideia.

Kaushal Modi
fonte
1

Depois de uma longa e dolorosa busca pelas funções perfeitas de 'avançar / retroceder', encontrei o seguinte com o qual agora estou muito feliz:

(progn
  (defun boundary ()
    (and      (= (char-syntax (char-after))  ?w)
         (not (= (char-syntax (char-before)) ?w))))
  (defun my-forward-word ()
    (interactive) 
    (while (progn (forward-char)  (not (boundary)))))
  (defun my-backward-word ()
    (interactive) 
    (while (progn (backward-char) (not (boundary)))))
  (global-set-key [M-right] 'my-forward-word)
  (global-set-key [M-left]  'my-backward-word)
  )
Ruy
fonte
0

Se você estiver disposto a usar evil, wno estado normal está vinculado evil-forward-word-begin, qual é a funcionalidade no estilo Vim que você procura.

Dan
fonte
Eu costumava usar evilhá muito tempo, mas há algum tempo eu uso god-modee ligações regulares do Emacs.
rekado
0

Costumo usar várias invocações de palavra direta seguidas de uma única palavra inversa para mover o ponto para o início de uma palavra em uma linha.

Como você mencionou, o truque é avançar duas palavras e depois uma palavra para trás.

A seguir, você deve executar o truque e respeitar outros modos, como o modo de subpalavras.

(define-key global-map (kbd  "M-f")
  (lambda ()
    (interactive)
    (forward-word)
    (forward-word)
    (backward-word)))

Esta é uma versão rudimentar de /emacs//a/4272/508 que não cobre alguns casos, mas é mais fácil de entender.

ustun
fonte