Vim editing multilinea come in sublimetext?


133

Ho iniziato a usare gvim e non riesco a capire come funzioni la modifica multilinea in gvim.

Per esempio:

Testo originale:

asd asd asd asd asd;
asd asd asd asd asd;
asd asd asd asd asd;
asd asd asd asd asd;
asd asd asd asd asd;
asd asd asd asd asd;
asd asd asd asd asd;

ctrl + q, jjjjjj, $ tutto è selezionato, quindi premo I per eseguire un inserimento multilinea.

La mia intenzione è quella di inserire le virgolette come nella prima riga, quindi premere Esc:

asd "asd asd" asd asd;
asd asd asd asd asd;
asd asd asd asd asd;
asd asd asd asd asd;
asd asd asd asd asd;
asd asd asd asd asd;
asd asd asd asd asd;

Quello che è successo? Mi aspettavo un comportamento simile a quello di sublimetext:

inserisci qui la descrizione dell'immagine

Se non sai come funziona, ripete semplicemente le azioni per ogni riga. Come può farlo? E cosa ci fa Vim qui?


Basta registrare una macro di tastiera per cambiare la prima riga e quindi riprodurre la macro per tutte le altre righe.
high5

Risposte:


215

Fatti un favore lasciando cadere il livello di compatibilità di Windows.

La normale scorciatoia per accedere alla modalità Visual-Block è <C-v>.

Altri si sono occupati della registrazione di macro, ecco alcune altre idee:

Utilizzando solo la modalità blocco visivo .

  1. Posiziona il cursore sulla seconda parola:

    asd |a|sd asd asd asd;
    asd asd asd asd asd;
    asd asd asd asd asd;
    asd asd asd asd asd;
    asd asd asd asd asd;
    asd asd asd asd asd;
    asd asd asd asd asd;
    
  2. Premi <C-v>per accedere alla modalità blocco visivo ed espandere la selezione verso il basso:

    asd [a]sd asd asd asd;
    asd [a]sd asd asd asd;
    asd [a]sd asd asd asd;
    asd [a]sd asd asd asd;
    asd [a]sd asd asd asd;
    asd [a]sd asd asd asd;
    asd [a]sd asd asd asd;
    
  3. Premi I"<Esc>per ottenere:

    asd "asd asd asd asd;
    asd "asd asd asd asd;
    asd "asd asd asd asd;
    asd "asd asd asd asd;
    asd "asd asd asd asd;
    asd "asd asd asd asd;
    asd "asd asd asd asd;
    
  4. Posiziona il cursore sull'ultimo carattere della terza parola:

    asd "asd as|d| asd asd;
    asd "asd asd asd asd;
    asd "asd asd asd asd;
    asd "asd asd asd asd;
    asd "asd asd asd asd;
    asd "asd asd asd asd;
    asd "asd asd asd asd;
    
  5. Premi <C-v>per accedere alla modalità blocco visivo ed espandere la selezione verso il basso:

    asd "asd as[d] asd asd;
    asd "asd as[d] asd asd;
    asd "asd as[d] asd asd;
    asd "asd as[d] asd asd;
    asd "asd as[d] asd asd;
    asd "asd as[d] asd asd;
    asd "asd as[d] asd asd;
    
  6. Premi A"<Esc>per ottenere:

    asd "asd asd" asd asd;
    asd "asd asd" asd asd;
    asd "asd asd" asd asd;
    asd "asd asd" asd asd;
    asd "asd asd" asd asd;
    asd "asd asd" asd asd;
    asd "asd asd" asd asd;
    

Con modalità blocco visivo e Surround.vim .

  1. Posiziona il cursore sulla seconda parola:

    asd |a|sd asd asd asd;
    asd asd asd asd asd;
    asd asd asd asd asd;
    asd asd asd asd asd;
    asd asd asd asd asd;
    asd asd asd asd asd;
    asd asd asd asd asd;
    
  2. Premi <C-v>per accedere alla modalità blocco visivo ed espandere la selezione verso il basso e verso destra:

    asd [asd asd] asd asd;
    asd [asd asd] asd asd;
    asd [asd asd] asd asd;
    asd [asd asd] asd asd;
    asd [asd asd] asd asd;
    asd [asd asd] asd asd;
    asd [asd asd] asd asd;
    
  3. Premi S"per circondare la tua selezione con ":

    asd "asd asd" asd asd;
    asd "asd asd" asd asd;
    asd "asd asd" asd asd;
    asd "asd asd" asd asd;
    asd "asd asd" asd asd;
    asd "asd asd" asd asd;
    asd "asd asd" asd asd;
    

Con modalità visuale e :normal.

  1. Premi Vper selezionare l'intera linea ed espanderla verso il basso:

    [asd asd asd asd asd;]
    [asd asd asd asd asd;]
    [asd asd asd asd asd;]
    [asd asd asd asd asd;]
    [asd asd asd asd asd;]
    [asd asd asd asd asd;]
    [asd asd asd asd asd;]
    
  2. Eseguire questo comando: :'<,'>norm ^wi"<C-v><Esc>eea"<CR>per ottenere:

    asd "asd asd" asd asd;
    asd "asd asd" asd asd;
    asd "asd asd" asd asd;
    asd "asd asd" asd asd;
    asd "asd asd" asd asd;
    asd "asd asd" asd asd;
    asd "asd asd" asd asd;
    
    • :norm[al]consente di eseguire i comandi in modalità normale su un intervallo di righe (la '<,'>parte viene aggiunta automaticamente da Vim e significa "agire sull'area selezionata")

    • ^ posiziona il cursore sul primo carattere della riga

    • w passa alla parola successiva

    • i"inserisce una "prima del cursore

    • <C-v><Esc>è il modo di Vim di inserire un carattere di controllo in questo contesto, qui è <Esc>usato per uscire dalla modalità di inserimento

    • ee si sposta alla fine della parola successiva

    • a"aggiunge un "dopo il cursore

    • <CR> esegue il comando

    Usando Surround.vim, il comando sopra diventa

    :'<,'>norm ^wvees"<CR>
    

7
Per i passaggi 4 e 5, consiglierei di premere gvper ripristinare la selezione visiva precedente, quindi spostarsi in orizzontale, magari con 2e. (Più righe, più prezioso gvè!)
joeytwiddle,

4
surround.vim usa un piccolo sin modalità normale ma uno grande Sin modalità visiva, quindi nel passaggio 3 del metodo surround.vim, i tasti dovrebbero essereS"
joeytwiddle

1
Il punto 3 di visual-block + Surround.vim dovrebbe essere S", nons"
zool

1
Invece dei passaggi 5 e 6 in modalità blocco visivo, puoi semplicemente posizionare il cursore dopo la terza parola e premere ..
Jonas,

2
Questo è interessante, ma funziona solo in alcuni casi in cui i caratteri che si desidera modificare su linee diverse si trovano esattamente nella stessa posizione orizzontale su ciascuna linea e le linee modificate si trovano una dopo l'altra. Non possiamo scegliere dove entrare in modalità modifica su quale linea in Vim? Possiamo in Sublim ... EDIT: In realtà la seconda risposta è quello che stavo cercando
Alexandre Bourlier,

30

Queste sono alcune buone soluzioni pronte all'uso sopra indicate, ma possiamo anche provare alcuni plugin che forniscono più cursori come Sublime.

Penso che questo appaia promettente:

Sembrava abbandonato da un po ', ma ha avuto alcuni contributi nel 2014.

È abbastanza potente, anche se mi ci è voluto un po 'di tempo per abituarmi al flusso (che è abbastanza simile al Sublime ma ancora modale come Vim).

Nella mia esperienza, se hai installato molti altri plugin, potresti incontrare alcuni conflitti!

Ci sono altri tentativi di questa funzione:

Non esitare a modificare se noti uno di questi in fase di miglioramento.


Sembra che github.com/osyo-manga/vim-over sia il più attivo del gruppo al momento.
Wernight,

Eccellente, questo è quello che stavo cercando
Alexandre Bourlier,

1
Dopo averne testato la maggior parte, hlissner / vim-multiedit sembra il migliore AFAIAC
Alexandre Bourlier,

1
Controlla mg979 / vim-visual-multi come un buon sostituto per i cursori multi-vim
Mushex Antaranian

29

Ci sono molti modi per farlo in Vim. Non so quali siano i più simili a quelli di Sublime Text.


Il primo sarebbe tramite la modalità di inserimento multilinea . Posiziona il cursore sulla seconda "a" nella prima riga, premi Ctrl-V, seleziona tutte le righe, quindi premi Ie inserisci una doppia virgoletta. Premendo <esc>si ripeterà l'operazione su ogni riga.


Il secondo è tramite macro. Posiziona il cursore sul primo carattere e inizia a registrare una macro con qa. Vai a destra con llll, inserisci la modalità di inserimento con a, metti una doppia virgoletta, esci dalla modalità di inserimento e torna all'inizio della riga con <home>(o equivalente). Premere jper spostarsi verso il basso di una riga. Interrompere la registrazione con q. E quindi riprodurre nuovamente la macro @a. Parecchie volte.


Qualcuno dei suddetti approcci funziona per te?


15

se si utilizza il comando "globale", è possibile ripetere ciò che è possibile fare in linea su un numero qualsiasi di righe.

:g/<search>/.<your ex command>

esempio:

:g/foo/.s/bar/baz/g

Il comando sopra trova tutte le linee che hanno pippo e sostituisce tutte le occorrenze di barra su quella linea con baz.

:g/.*/

farà su ogni linea


1
È così utile, non lo sapevo. Sembra una combinazione di comandi così potente e intelligente.
0xc0de,

Per comodità, ho scritto una piccola funzione che prende la parola sotto il cursore (o la parola visivamente selezionata), richiede una sostituzione e quindi esegue il :gcomando descritto qui. Mi piace usare /gcper chiedere "conferme" in modo da poter premere yo nper ogni sostituzione, o aper cambiarle tutte.
joeytwiddle,

11
Ctrl-v ................ start visual block selection
6j .................... go down 6 lines
I" .................... inserts " at the beginning
<Esc><Esc> ............ finishes start
2fdl. ................. second 'd' l (goes right) . (repeats insertion)

Nel passaggio 3, Inon è possibile accedere alla modalità di inserimento, sai perché questo accade?
Ninja

Prova a caricare vim senza plug-in: vim -u NONEe prova a eseguire di nuovo l'azione desiderata, potrebbe essere una mappa o un plug-in a cambiare il comportamento del tuo vim.
SergioAraujo,

6

Non sono sicuro di cosa vimstia facendo, ma è un effetto interessante. Il modo in cui stai descrivendo ciò che desideri sembra più simile al modo in cui funzionano le macro ( :help macro). Qualcosa del genere farebbe quello che vuoi con le macro (partendo dalla modalità normale):

  1. qa: Registra la macro da aregistrare.
  2. 0w: 0vai all'inizio della riga, wsalta una parola.
  3. i"<Esc>: Consente di accedere alla modalità di inserimento, inserire a "e tornare alla modalità normale.
  4. 2e: Passa alla fine della seconda parola.
  5. a"<Esc>: Aggiungi a ".
  6. jq Passa alla riga successiva e termina la registrazione macro.

Presi insieme: qa0wi"<Esc>2ea"<Esc>

Ora puoi eseguire la macro con @a, ripeti l'ultima macro con @@. Per applicare al resto del file, fare qualcosa del genere 99@ache presuppone che non ci siano più di 99 righe, l'esecuzione della macro termina quando raggiunge la fine del file.

Ecco come ottenere ciò che vuoi visual-block-mode(partendo dalla modalità normale):

  1. Vai dove vuoi che sia la prima citazione.
  2. Invio visual-block-mode, selezionare le linee che si desidera influenzare, Gper andare in fondo al file.
  3. Hit I"<Esc>.
  4. Passa al punto successivo che desideri inserire a ".
  5. Vuoi ripetere quello che hai appena fatto, quindi .sarà sufficiente una semplice .

4
Non è necessario per 99 @ a. Se si desidera eseguire una macro su ogni riga di un file, provare:% norm! @un.
Rook

Senza i punti (sono solo le estremità delle frasi, non fanno parte dei comandi)
Arriva il

9999@apuò essere brutto ma è molto più facile da scrivere rispetto a :%norm! @ae non viene eseguito nuovamente sulla riga appena modificata. Comunque buono conoscerlo comunque. :)
joeytwiddle,

0

La mia soluzione è utilizzare questi 2 mapping:

map <leader>n <Esc><Esc>0qq
map <leader>m q:'<,'>-1normal!@q<CR><Down>

Come usarli:

  1. Seleziona le tue linee. Se voglio selezionare le successive 12 righe premoV12j
  2. stampa <leader>n
  3. Apporta le modifiche alla linea
  4. Assicurati di essere in modalità normale, quindi premi <leader>m

Per effettuare un'altra modifica non è necessario ripetere la selezione. Basta premere <leader>n, apportare la modifica e premere <leader>mper applicare.


Come funziona:

  • <Esc><Esc>0qq Esci dalla selezione visiva, vai all'inizio della riga e inizia a registrare una macro.

  • q Interrompere la registrazione della macro.

  • :'<,'>-1normal!@q<CR> Dall'inizio della selezione visiva alla riga prima della fine, riprodurre la macro su ciascuna riga.

  • <Down> Torna all'ultima riga.


Puoi anche mappare la stessa chiave ma per diverse modalità:

vmap <leader>m <Esc><Esc>0qq
nmap <leader>m q:'<,'>-1normal!@q<CR><Down>

Anche se questo confonde la tua capacità di fare un'altra modifica. Dovrai riselezionare le tue linee.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.