4

I've toying with someone else's .vimrc file. I'm getting an error on a function call within the .vimrc file.

Error detected while processing <FILE>:
line 1500:
E492: Not an editor command: EQAS_Align('\S:',         '',   '\s')
line 1501:
E492: Not an editor command: EQAS_Align('[[:punct:]]', '',   '\s')

Lines 1500 and 1501 are as follows:

EQAS_Align('\S:',         '',   '\s')
EQAS_Align('[[:punct:]]', '',   '\s')

There is a plugin in ~/.vim/plugin directory that accompanied this .vimrc configuration that has the following function in it:

function EQAS_Align (mode, ...) range
  let option = a:0 ? a:1 : {}

  <snip>

endfunction

I'm not sure what the problem is and I don't know enough about VIM scripting to fix this.

EDIT

This line is in the .vimrc file before these functions are called: runtime plugin/eqalignsimple.vim

  • 1
    May I ask why there is an action that seems to modify the current buffer in your .vimrc ? You'd better extract these :call to EQAS_Align to another function or to a macros file. This way the action will be executed only when you explicitly request so. – Luc Hermitte Feb 14 '17 at 18:14
  • I have no idea. It's someone else's vim file I'm studying. – StevieD Feb 14 '17 at 18:31
4

It seems that the following 2 lines:

EQAS_Align('\S:',         '',   '\s')
EQAS_Align('[[:punct:]]', '',   '\s')

... refer to a custom function named EQAS_Align().

It depends on what you want to do with it, but if you want its code to be processed, you have to prefix its name with the :call command:

call EQAS_Align('\S:',         '',   '\s')
call EQAS_Align('[[:punct:]]', '',   '\s')

To read its return value, you can use the :echo command:

echo EQAS_Align('\S:',         '',   '\s')
echo EQAS_Align('[[:punct:]]', '',   '\s')

To assign its value to a variable, you can use the :let command:

let your_var1 = EQAS_Align('\S:',         '',   '\s')
let your_var2 = EQAS_Align('[[:punct:]]', '',   '\s')

To bind it to some keys in normal mode, you can use the :nnoremap command:

nnoremap <key1> :call EQAS_Align('\S:',         '',   '\s')<CR>
nnoremap <key2> :call EQAS_Align('[[:punct:]]', '',   '\s')<CR>

To bind it to a custom command, you can use the :command command:

command! YourCommand1 call EQAS_Align('\S:',         '',   '\s')
command! YourCommand2 call EQAS_Align('[[:punct:]]', '',   '\s')

Regarding the function itself:

function EQAS_Align (mode, ...) range
  let option = a:0 ? a:1 : {}

  <snip>

endfunction

You probably want to add a bang after the function keyword, otherwise Vim will complain each time you re-source your vimrc because it won't be able to overwrite the old definition:

Error detected while processing /home/user/.vimrc:
line XXX:
E122: Function EQAS_Align already exists, add ! to replace it

The function is defined with the range attribute, which means that if you pass a range to the :call command, the function will be called only once. Which probably means that it will handle the range itself, using the variables a:firstline and a:lastline (see :h :func-range).

After the named argument mode, it accepts the argument ..., which means that you could pass up to 20 more optional arguments. If there are optional arguments, inside the function, you can access them with the variables a:1, a:2, and so on; or with the list a:000.
a:0 is the number of optional arguments (see :h a:0).


The line:

let option = a:0 ? a:1 : {}

… is an assignment which uses a conditional expression (see :h expr1).
The expression tests whether a:0 is different than 0. If it is, then the variable option is assigned the value a:1, otherwise the value {}.
It means that if there are optional arguments, then the value of option should be the first optional argument, otherwise it should be an empty dictionary.

You could probably do something similar using the get() function:

let option = get(a:, '1', {})

… which means: take the dictionary a: (which contains all the arguments of the function), and look for the key 1 (first argument of the function). If you find the key, then return its associated value. If you don't find it, then return {}.

  • Thanks, yeah, the issue was no call in front of the function. Unfortunately, the plugin throws a bunch of other errors that complain about bad arguments. A problem for another day. – StevieD Feb 14 '17 at 18:11
2

Based on :help startup, vimrc files (section 3) are loaded before plugins (section 4), so it makes sense that you wouldn't be able to use plugin-defined functions in your ~/.vimrc.

Section 4 does note that plugin loading is equivalent to :runtime! plugin/**/*.vim You could call that in your ~/.vimrc before the lines calling your plugin's function, or you could use a narrower command such as :runtime! plugin/my_plugin.vim to only load my_plugin.

Note that either of these may result in the plugin(s) being loaded twice; once while loading your ~/.vimrc and once during regular plugin loading. Off the top of my head, I know that can potentially cause problems with defining autocommands twice. :help :autocmd provides some suggestions for how to deal with that, if your plugin uses autocommands, you may want to check and make sure it protects itself.

  • This line is in the .vimrc. I forgot to include it in my question: runtime plugin/eqalignsimple.vim – StevieD Feb 14 '17 at 18:02
  • @StevieD Ah, in that case, user9433424's answer is probably your solution. – 8bittree Feb 14 '17 at 18:04

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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