jose-villar

Notes written in markdown

View on GitHub

Mapping An Operator map-operator

An operator is used before a {motion} command. To define your own operator you must create mapping that first sets the operatorfunc option and then invoke the g@ operator. After the user types the {motion} command the specified function will be called.

g@{motion} Call the function set by the operatorfunc option. The '[ mark is positioned at the start of the text moved over by {motion}, the '] mark on the last character of the text. The function is called with one String argument: line {motion} was linewise char {motion} was characterwise block {motion} was blockwise-visual

Although block would rarely appear, since it can only result from Visual mode where g@ is not useful.

Here is an example that counts the number of spaces with <F4>:

      nmap `<silent>`{=html} `<F4>`{=html} :set opfunc=CountSpaces`<CR>`{=html}g@ vmap `<silent>`{=html} `<F4>`{=html} :`<C-U>`{=html}call CountSpaces(visualmode(), 1)`<CR>`{=html}

      function! CountSpaces(type, ...) let sel_save = &selection let &selection = "inclusive" let reg_save = @@

          if a:0  " Invoked from Visual mode, use gv command.
            silent exe "normal! gvy"
          elseif a:type == 'line'
            silent exe "normal! '[V']y"
          else
            silent exe "normal! `[v`]y"
          endif

          echomsg strlen(substitute(@@, '[^ ]', '', 'g'))

          let &selection = sel_save
          let @@ = reg_save

      endfunction

Note that the selection option is temporarily set to inclusive to be able to yank exactly the right text by using Visual mode from the '[ to the '] mark

Replace a series of asterisk bullet points with a numbered list

    :let c=0 | g/^* /let c+=1 | s//\=c.'. '

First it initializes the variable c then it executes the global command g which looks for the pattern ^* Whenever a line containing this pattern is found, the global command executes the command let c+=1 | s//\=c.'. ' It increments the variable c, then it substitutes (//) with the evaluation of an expression (\=): the contents of variable c concatenated (.) with the string '. '

To make a command, you can use:

    command! -range=% NumberedLists let [c,d]=[0,0] | <line1>,<line2>g/^/let [c,d]=[line('.')==d+1 ? c+1 : 1, line('.')] | s//\=c.'. '

Variables

The scope name by itself can be used as a Dictionary. For example, to delete all script-local variables:

    :for k in keys(s:)
    :    unlet s:[k]
    :endfor

The behavior of == depends on a user’s settings.