6

Sto cercando un modo per determinare il tipo di file di un file in vim e impostare l'evidenziazione della sintassi in base al tipo di file. L'unico problema è che non posso usare l'estensione del file per determinare il tipo di file.Rileva il tipo di file in vim senza estensione file valida

Questo è il mio scenario: io uso vimdiff o gvimdiff come il mio P4DIFF strumento, che mostra le modifiche tra i file nella mia copia locale e quelli dal server per forza. Perforce sembra portare nelle file dal server per forza nella directory/tmp e utilizza il PID dare un nome al file, ad esempio:

/tmp/tmp.24673.23 

Questo è stato per un file sorgente C++.

I tipi di file più frequenti che ho incontrato nel repository perforce sono sorgenti C/C++ e file header, Makefile, script python, script perl, script ruby ​​e script tcl.

  • ho guardato in utilizzando modeline, ma la maggior parte delle fonti in nostro albero non ho queste informazioni incorporate nel file.

  • This post menzioni su un possibile approccio per cercare e identificare un modello magico. Non sono riuscito a trovare alcun modello magico coerente con cui avrei potuto ottenere un alto tasso di successo.

  • Provato usando il binario file sulla mia macchina Linux per vedere quali risultati ottengo. Sembra di identificare ben fonti C/C++, ma non riesce per Makefiles e anche gli script Python (che non hanno la hashbang)

Una cosa buona è che, tra i 2 file che vengono confrontati, il file a destra proviene dalla mia copia locale e quindi ha il nome file corretto con estensione, pertanto l'evidenziazione della sintassi è abilitata correttamente per il file sulla destra.

C'è un modo in cui potrei sfruttare questo per impostare la stessa evidenziazione della sintassi per il file visualizzato a sinistra?

Sono inoltre benvenute eventuali soluzioni alternative a questo problema.

risposta

6

questo è stato un interessante puzzle. :)

aug SmartDiffType 
    au! 
    au VimEnter * :if &diff && len(&ft) | call setwinvar(2/winnr(),'&ft',&ft) | elseif &diff | let &ft=getwinvar(2/winnr(),'&ft') | endif 
aug END 

Note:

  • delle 4 linee di cui sopra, è solo necessità la linea au VimEnter, ma in generale è una buona pratica per mettere autocomandi in qualche gruppo autocomando con un reset (au!) nella parte superiore.
  • AutoCommand su VimEnter perché altrimenti diff o le finestre non sono adeguatamente ancora
  • vimdiff inizializzata potrebbe essere stato innescato con il vecchio file a destra oa sinistra dello split, quindi consideriamo entrambi i casi.
  • Il 2/winnr() è un trucco matematica per capovolgere tra 1 e 2 (2/2 = 1, 2/1 = 2)
+0

Molto bello. Adoro il trucco '2/winnr()' !! –

+0

Fantastico! Funziona davvero bene ... Ho appena spostato l'if-end in una funzione e ho sostituito il comando con una chiamata alla funzione. :) – Tuxdude

3

Supponendo di avere aperto solo i 2 si divide e la spaccatura a sinistra è il vostro file locale è possibile effettuare le seguenti operazioni

:windo let &ft = getwinvar(1, '&ft') 

Questo imposterà la filetype al valore della parte superiore più finestra di sinistra per tutte le finestre

Per maggiori spiegazioni, vedi:

:h :windo 
:h 'ft' 
:h getwinvar(
+0

Grazie, funziona. Ho dovuto usare 'windo let & ft = getwinvar (2, '& ft')' dato che la finestra di destra aveva il tipo di file corretto. C'è un modo per aggiungerlo a '.vimrc' in modo che per ogni vimdiff lo faccia automaticamente? Aggiungere semplicemente il comando 'windo' a .vimrc non ha funzionato. Immagino che in seguito possa essere superato. – Tuxdude

+0

Anche se sono sicuro che un simile "autocmd" potrebbe essere creato, sento che la soluzione più semplice sarebbe quella di creare un comando personalizzato: "command! -bar -nargs = 0 SameFiletype exe 'windo set ft ='. & ft 'Aggiungi questo al tuo file '~/.vimrc'. La prossima volta che si verifica la situazione, spostati nel buffer con il tipo di file corretto ed esegui ': SameFiletype' –

+0

Grazie, sembra un approccio ragionevole :) – Tuxdude