I am practicing some vimscript and, although there are very good plugins out there, I am writing a function for commenting/uncommenting code for the matter of experimenting.

So far, I wrote the following:

def g:MyComment(comment_symbol: string)
    if trim(getline("."))[0] == comment_symbol
        normal! ^2x

augroup commenting_blocks_of_code
    autocmd FileType c,cpp,java.      b:comment_symbol = '// '
    autocmd FileType sh,vim,python    b:comment_symbol = '# '
    autocmd FileType tex              b:comment_symbol = '% '
augroup END

The function works well for uncommenting one line.

However, I wish to add the string comment_symbol .. " " at the beginning of the current line in position ^ but I cannot figure out how, i.e. I have to fill the ????? line according to the mentioned requirements.

If possible, I would like to use builtin vim functions.

The next step would be to modify my function so that it can accept a start_line and an end_line as argument, i.e. I want to modify my function signature with def g:MyComment(start_line: number, end_line:number, comment_symbol: string) so that I can comment/uncomment a bunch of lines picked e.g. by a selection in Visual mode or by explicitly specifying a range.

Then, I can throw everything and install vim-commentary. :D


1 Answer 1


To put the value of b:comment_symbol at the beginning of a line, you can use

execute "normal 0i" . b:comment_symbol

Or, if you want to put your comment symbol before the first non-whitespace character (i.e. have your comments follow existing indentation), use

execute "normal I" . b:comment_symbol

Maybe there are more elegant solutions. I tried to find one that fits into the style of your code.

Having said that, I think that the :substitute command is much better suited for this task:


I also don't think that whitespace should be part of b:comment_symbol. Instead, it should be appended when inserting or removed when removing the comment. As your code is currently written, removing a C, C++ or Java comment will leave in one space while removing a comment from the (python) line #foo will chop off the f.

  • Thanks. I agree, adding that whitespace may create troubles. Now I have everything working well in my .vimrc. However, when I open a .py file and i run the function I get E121: undefined variable b:comment_symbol. Do you know why?
    – Barzi2001
    Mar 27, 2023 at 10:47
  • @Barzi2001 That may be worth its own question. I did not try out your autocommands, instead I just did :let b:comment_symbol='# ' for testing. In vim9script, var is used, while in legacy, it's let.
    – Friedrich
    Mar 27, 2023 at 10:58

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.