2010-10-26 9 views
26

Vom mächtigen PEP 8:Vim: Verwenden Sie kürzere Textbreite in den Kommentaren und Docstrings

[P] Leasing Grenze alle Linien auf maximal 79 Zeichen. Für fließende lange Textblöcke (Docstrings oder Kommentare) wird empfohlen, die Länge auf 72 Zeichen zu beschränken.

Beim Bearbeiten von Python-Code in Vim, stelle ich meinen textwidth-79 und Vim wickelt automatisch lange Zeilen Python-Code für mich, wenn ich die Zeichenbegrenzung getroffen.

Aber in Kommentaren und Docstrings, muss ich stattdessen Text mit 72 Zeichen umbrechen. Gibt es eine Möglichkeit, Vim automatisch auf textwidth auf 72 zu setzen, wenn ich mich in einem Kommentar oder DocString befinde, und es zurücksetze, wenn ich fertig bin?

+3

Sehr ähnliche Frage: http://stackoverflow.com/questions/3475072/vim-different-textwidth-for-multiline-c-comments – adw

Antwort

14

Also ich habe noch nie Vim Scripting gemacht, aber basierend auf this question about doing something similar in C und this tip for checking if you're currently in a comment habe ich eine Lösung zusammengehackt.

verwendet standardmäßig das die PEP8-vorgeschlagenen Breite von 79 Zeichen für normale Zeilen und 72 Zeichen für Kommentare, aber man kann sich durch let ting g:python_normal_text_width oder g:python_comment_text_width Variablen bzw. außer Kraft setzen. (Persönlich wickle ich normale Zeilen mit 78 Zeichen.)

Drop dieses Baby in Ihrem .vimrc und Sie sollten gut gehen. Ich kann das später als Plugin verpacken.

function! GetPythonTextWidth() 
    if !exists('g:python_normal_text_width') 
     let normal_text_width = 79 
    else 
     let normal_text_width = g:python_normal_text_width 
    endif 

    if !exists('g:python_comment_text_width') 
     let comment_text_width = 72 
    else 
     let comment_text_width = g:python_comment_text_width 
    endif 

    let cur_syntax = synIDattr(synIDtrans(synID(line("."), col("."), 0)), "name") 
    if cur_syntax == "Comment" 
     return comment_text_width 
    elseif cur_syntax == "String" 
     " Check to see if we're in a docstring 
     let lnum = line(".") 
     while lnum >= 1 && (synIDattr(synIDtrans(synID(lnum, col([lnum, "$"]) - 1, 0)), "name") == "String" || match(getline(lnum), '\v^\s*$') > -1) 
      if match(getline(lnum), "\\('''\\|\"\"\"\\)") > -1 
       " Assume that any longstring is a docstring 
       return comment_text_width 
      endif 
      let lnum -= 1 
     endwhile 
    endif 

    return normal_text_width 
endfunction 

augroup pep8 
    au! 
    autocmd CursorMoved,CursorMovedI * :if &ft == 'python' | :exe 'setlocal textwidth='.GetPythonTextWidth() | :endif 
augroup END 
+3

Gibt es einen spürbaren Effekt auf die Leistung durch die Verwendung der CursorMoved * -Gruppen? Ich benutze eine ähnliche Methode, aber wählte die 'InsertEnter' Au-Gruppe anstelle von CursorMoved *. CursorMoved ist definitiv feinkörniger, aber 'InsertEnter' war für mich ausreichend feinkörnig und wird viel seltener aufgerufen. Ich wollte es nur als Option erwähnen und auch prüfen, ob bei "CursorMoved" Leistungsprobleme auftreten. –

+0

@Herbert Sitz Ich habe keine Leistungsprobleme mit CursorMoved bemerkt. Es macht dieses Skript natürlicher für die Neuformatierung bestehender Docstrings, oder wenn Sie wie ich neu bei Vim sind und sich im Einfügemodus noch viel bewegen. Aber die Verwendung von InsertEnter wird definitiv die üblichen Verwendungen erfassen und weniger Ressourcen verbrauchen. –

+1

Das ist genial; danke für das zusammenstellen. Ich habe festgestellt, dass der synIDattr Aufruf in meinem vim-Setup zu "Constant" führt, nicht zu "String", wenn ich in einem String-Literal bin. Ich musste dagegen in meinem vimrc als Option vergleichen. – adrian

4

Die angenommene Antwort ist großartig! Es unterstützt jedoch nicht die Gewohnheit, die ich zum Formatieren/Bearbeiten von Kommentaren habe: Ich mache meine Bearbeitungen und verwende dann den gqj-Befehl, der im Wesentlichen lautet "Neuformatierung der aktuellen Zeile mit der nächsten". Dann treffe ich '.' um dies für jede Zeile zu wiederholen (der Befehl selbst bringt den Cursor zur nächsten Zeile). Ich kenne die vim-Skriptsprache nicht sehr gut, daher könnte jemand in der Lage sein, die akzeptierte Antwort zu unterstützen. In der Zwischenzeit haben, was ich getan ist eine Funktionstaste (F6) ordnen Sie die Textbreite bis 72, formatieren Sie die Linie zu ändern und dann die Textbreite bis 79.

nmap <F6> :set textwidth=72<CR>gqj:set textwidth=79<CR> 

Jetzt wieder ändern, wenn ich in ein bin Docstring, ich mache nur die Bearbeitung, (ESC) und dann F6 wiederholt drücken, bis alle Zeilen richtig formatiert sind.

Ich habe meinen map-Befehl und das akzeptierte Antwort-Skript zu meiner .vim/after/ftplugin/python.vim hinzugefügt.

Verwandte Themen